ARTICLE DETAIL

资讯详情

深耕网站建设与运营推广的一线实战洞察。

Jspreadsheet 嵌套表头(nestedHeaders)实战指南:多层级列头配置与源码解析

Jspreadsheet 嵌套表头(nestedHeaders)实战指南:多层级列头配置与源码解析 前端UI组件【免费下载链接】ceJspreadsheet is a lightweight JavaScript data grid component for creating interactive data grids with advanced spreadsheet controls.项目地址https://gitcode.com/gh_mirrors/ce/ce点击查看免费下载Jspreadsheetjspreadsheet-ce是一款轻量级的 JavaScript 数据网格组件其nestedHeaders配置项允许你在单一工作表内构建多层级的分组列头如大区 → 国家 / 商品 / 库存无需任何第三方插件。本文以仓库中 v4 嵌套表头示例 和 v5 当前文档 为核心脉络完整覆盖配置语法、四框架示例原生 JS / React / Vue / Angular并结合 src/utils/internal.js、src/utils/columns.js 等源码讲解其底层渲染与动态调整机制。读完本文你将掌握如何声明嵌套表头、如何让嵌套表头在增删列、撤销重做时自动保持 colspan 正确以及如何将嵌套表头一并导出到 CSV。nestedHeaders 是什么一个配置项撑起的分层级表头在 Jspreadsheet 中普通列头通过columns[].title设置只会生成一行tr。而nestedHeaders允许你声明多行表头结构每行由若干表头单元格组成每个单元格通过colspan横向合并若干列从而形成类似 Excel 的分组表头层级。从 v5 文档 可以确认其类型定义属性说明nestedHeaders: { id?: string; colspan?: number; title?: string; align?: string; }[][]工作表Worksheet的嵌套表头定义其中外层数组的每一项对应一行表头一个tr内层数组的每一项对应一个合并后的表头单元格。每个单元格支持四个属性title单元格显示的文本colspan该单元格横向跨越的列数缺省时按 1 处理align单元格内文本对齐方式缺省为centerid为单元格设置 HTMLid属性便于后续定位和样式控制。完整示例从 v4 原生写法到 v5 多框架写法v4 原生 HTML 示例仓库原样继承仓库中的 v4 示例文档 给出了最精简的嵌套表头用法。示例定义了三列国家/食品/库存并在其上方叠加两层嵌套表头第一层用colspan: 3将整张表合并为Supermarket information第二层拆分为Location跨 1 列与Other Information跨 2 列html !-- 原文档示例直接引用在线 CDN 资源这里以本地 npm 安装路径示意效果等价 实际项目中可按构建产物或 jspreadsheet-ce 包方式引入 -- script srcnode_modules/jspreadsheet-ce/dist/jspreadsheet.js/script script srcnode_modules/jsuites/dist/jsuites.js/script link relstylesheet hrefnode_modules/jspreadsheet-ce/dist/jspreadsheet.css typetext/css / link relstylesheet hrefnode_modules/jsuites/dist/jsuites.css typetext/css / div idspreadsheet/div script var data [ [BR, Cheese, 1], [CA, Apples, 0], [US, Carrots, 1], [GB, Oranges, 0], ]; let table jspreadsheet(document.getElementById(spreadsheet), { data:data, columns: [ { type: autocomplete, title: Country, width: 300, url: /jspreadsheet/countries }, { type: dropdown, title: Food, width: 150, source: [Apples,Bananas,Carrots,Oranges,Cheese] }, { type: checkbox, title: Stock, width:100 }, ], nestedHeaders:[ [ { title: Supermarket information, colspan: 3, }, ], [ { title: Location, colspan: 1, }, { title: Other Information, colspan: 2 } ], ] }); /script /html注意两个细节v4 示例中nestedHeaders直接挂在jspreadsheet()顶层配置上与data、columns平级而 v5 起配置被组织进worksheets数组嵌套表头随之挂到每个工作表内部第二层表头的单元格colspan之和1 2正好等于第一层的colspan3也正好等于数据列数3 列。虽然组件本身不会强制校验这个等式的成立但只有按此规则设计层级关系才能在视觉上正确对齐。v5 多框架写法React / Vue / Angularv5 文档 在原生写法之上进一步给出四个框架的等价实现。其配置统一放进worksheets[0]并用minDimensions指定最小网格尺寸。以原生 JS 为例div idspreadsheet/div script // Create the spreadsheet let table jspreadsheet(document.getElementById(spreadsheet), { worksheets: [{ data: [ [BR, Cheese, 1], [CA, Apples, 0], [US, Carrots, 1], [GB, Oranges, 0], ], columns: [ { type: autocomplete, title: Country, width: 200px }, { type: dropdown, title: Food, width: 100px, source: [Apples,Bananas,Carrots,Oranges,Cheese] }, { type: checkbox, title: Stock, width: 100px }, { type: number, title: Price, width: 100px }, ], minDimensions: [6,4], nestedHeaders:[ [ { title: Supermarket information, colspan: 6 }, ], [ { title: Location, colspan: 1 }, { title: Other Information, colspan: 2 }, { title: Costs, colspan: 3 }, ], ] }] }); /script这个 v5 示例演示了更典型的三段式分组第一层整行合并colspan: 6与minDimensions的 6 列对齐第二层按 1 / 2 / 3 拆分分别对应 Location、Other Information、Costs 三个分组。React写法来自 jspreadsheet-ce/react 包 对应的 React 封装通过Worksheet子组件传入nestedHeaders与minDimensionsimport React, { useRef } from react; import { Spreadsheet, Worksheet } from jspreadsheet-ce/react; import jsuites/dist/jsuites.css; import jspreadsheet-ce/dist/jspreadsheet.css; export default function App() { const spreadsheet useRef(); const data [ [BR, Cheese, 1], [CA, Apples, 0], [US, Carrots, 1], [GB, Oranges, 0], ]; const columns [ { type: autocomplete, title: Country, width: 200px }, { type: dropdown, title: Food, width: 100px, source: [Apples,Bananas,Carrots,Oranges,Cheese] }, { type: checkbox, title: Stock, width: 100px }, { type: number, title: Price, width: 100px }, ]; const nestedHeaders [ [ { title: Supermarket information, colspan: 8 } ], [ { title: Location, colspan: 1 }, { title: Other Information, colspan: 2 }, { title: Costs, colspan: 5 }, ], ]; return ( Spreadsheet ref{spreadsheet} Worksheet data{data} columns{columns} nestedHeaders{nestedHeaders} minDimensions{[8,4]} / /Spreadsheet ); }Vue写法jspreadsheet-ce/vue与 React 结构一一对应通过:nestedHeaders绑定响应式数据template Spreadsheet refspreadsheet Worksheet :datadata :columnscolumns :nestedHeadersnestedHeaders :minDimensions[8,4] / /Spreadsheet /template script setup import { ref } from vue import { Spreadsheet, Worksheet } from jspreadsheet-ce/vue; import jsuites/dist/jsuites.css; import jspreadsheet-ce/dist/spreadsheet.css; const data ref([ [BR, Cheese, 1], [CA, Apples, 0], [US, Carrots, 1], [GB, Oranges, 0], ]); const columns ref([ { type: autocomplete, title: Country, width: 200px }, { type: dropdown, title: Food, width: 100px, source: [Apples,Bananas,Carrots,Oranges,Cheese] }, { type: checkbox, title: Stock, width: 100px }, { type: number, title: Price, width: 100px }, ]); const nestedHeaders ref([ [ { title: Supermarket information, colspan: 8 } ], [ { title: Location, colspan: 1 }, { title: Other Information, colspan: 2 }, { title: Costs, colspan: 5 }, ], ]); const spreadsheet ref(null); /scriptAngular写法Standalone 组件在ngAfterViewInit中通过jspreadsheet工厂创建实例配置对象与原生 JS 完全一致import { Component, ViewChild, ElementRef } from angular/core; import jspreadsheet from jspreadsheet-ce; import jspreadsheet-ce/dist/jspreadsheet.css import jsuites/dist/jsuites.css Component({ standalone: true, selector: app-root, template: div #spreadsheet/div, }) export class AppComponent { ViewChild(spreadsheet) spreadsheet: ElementRef; worksheets: jspreadsheet.worksheetInstance[]; ngAfterViewInit() { this.worksheets jspreadsheet(this.spreadsheet.nativeElement, { worksheets: [{ data: [ [BR, Cheese, 1], [CA, Apples, 0], [US, Carrots, 1], [GB, Oranges, 0], ], columns: [ { type: autocomplete, title: Country, width: 200px }, { type: dropdown, title: Food, width: 100px, source: [Apples,Bananas,Carrots,Oranges,Cheese] }, { type: checkbox, title: Stock, width: 100px }, { type: number, title: Price, width: 100px }, ], minDimensions: [8,4], nestedHeaders:[ [ { title: Supermarket information, colspan: 8 } ], [ { title: Location, colspan: 1 }, { title: Other Information, colspan: 2 }, { title: Costs, colspan: 5 }, ], ] }] }); } }四个框架示例在 React / Vue 中还将colspan扩展到了 8与minDimensions: [8,4]对齐可见colspan与minDimensions的第一维保持一致的惯用做法。源码解析嵌套表头如何被渲染出来初始化阶段把配置变成多行tr工作表创建时src/utils/worksheets.js 会在构建thead的过程中检测options.nestedHeaders只要第一行第一个单元格存在有效配置就为每一行嵌套表头调用createNestedHeader并追加到thead// src/utils/worksheets.js if (obj.options.nestedHeaders obj.options.nestedHeaders.length 0 obj.options.nestedHeaders[0] obj.options.nestedHeaders[0][0]) { for (let j 0; j obj.options.nestedHeaders.length; j) { obj.thead.appendChild(createNestedHeader.call(obj, obj.options.nestedHeaders[j])); } }也就是说嵌套表头会渲染在普通列头行之前形成分组行 列头行的堆叠结构。createNestedHeader每个单元格的完整语义src/utils/internal.js 中的createNestedHeader是嵌套表头的核心渲染函数其处理逻辑揭示了配置项的完整语义默认值兜底colspan缺省为 1title缺省为空字符串id缺省为空字符串——因此文档类型定义中所有字段均为可选隐藏列兼容遍历单元格覆盖的列数时若某列类型为hidden会自动把有效列数 1避免隐藏列导致合并错位单元格属性生成的td会写入data-column记录该单元格覆盖的列索引以逗号分隔、colspan、align缺省center与id文本内容即title行标记整行tr添加jss_nested类首列还保留一个jss_selectall单元格用于承载行选择功能这正是嵌套表头行从列 0开始渲染的原因。// src/utils/internal.js节选 tr.classList.add(jss_nested); const td document.createElement(td); td.classList.add(jss_selectall); ... td.setAttribute(data-column, column.join(,)); td.setAttribute(colspan, nestedInformation[i].colspan); td.setAttribute(align, nestedInformation[i].align || center); td.setAttribute(id, nestedInformation[i].id); td.textContent nestedInformation[i].title;同时渲染函数会把该行的 DOM 元素回写到配置对象nestedInformation.element tr为后续动态调整如修改 colspan预留了直接的操作句柄。动态行为增删列与撤销重做时的自动修正嵌套表头不是静态贴图。仓库源码在以下三处对nestedHeaders做了联动修正插入列src/utils/columns.js 在插入列后遍历每一行嵌套表头将该行最后一个单元格的colspan加上新增列数并同步更新 DOM 上的colspan属性——新增列会被自动并入最后一组删除列src/utils/columns.js 执行相反的减法操作同样作用于每行最后一个单元格撤销 / 重做src/utils/history.js 在恢复插入列type 为删除方向时或撤销删除type 为插入方向时的历史记录时按historyRecord.numOfColumns对最后一个单元格的colspan做增减。这种只修正每行最后一个单元格的设计意味着如果你在删除列后想让某个中间分组收缩可能需要结合setHeader/配置更新自行调整但从默认行为看动态增删列不会破坏嵌套表头的整体行数结构。导出与复制嵌套表头随 CSV 一起输出在 src/utils/copyPaste.js 中当复制或下载数据且开启了表头导出obj.parent.config.includeHeadersOnDownload true或调用时显式传入includeHeaders时组件会把nestedHeaders逐行转换为 CSV 文本每个单元格输出title其后按colspan - 1补充空字符串占位最终行间以\r\n分隔// src/utils/copyPaste.js节选 if (obj.options.nestedHeaders obj.options.nestedHeaders.length 0) { tmp obj.options.nestedHeaders; for (let j 0; j tmp.length; j) { const nested []; for (let i 0; i tmp[j].length; i) { const colspan parseInt(tmp[j][i].colspan); nested.push(tmp[j][i].title); for (let c 0; c colspan - 1; c) { nested.push(); } } nestedHeaders nested.join(delimiter) \r\n; } }因此导出的 CSV 会在数据行之前包含完整的嵌套表头层级供下游报表或表格工具直接消费。与普通表头的协同title、onchangeheader 与历史记录嵌套表头解决的是列分组展示问题而普通列头仍有自己的编程接口两者互补。仓库 src/utils/headers.js 提供了三个方法其行为被 test/headers.js 中的测试用例逐一验证方法说明getHeader(column)获取指定列从 0 起的表头文本直接读取obj.headers[column].textContentgetHeaders(asArray)获取全部表头asArray为真时返回数组否则返回以csvDelimiter拼接的字符串setHeader(column, newValue)设置列头文本传入空字符串或undefined时自动回退为默认列名如 A、B、C并触发onchangeheader事件setHeader的实现细节值得注意src/utils/headers.js同步更新 DOM 文本、title属性以及options.columns[column].title保证配置与界面一致将操作写入历史setHistory因此undo()/redo()可以回退/重放表头修改——test/headers.js 专门为此提供了测试派发onchangeheader(instance, colIndex, newValue, oldValue)事件供业务侧监听表头变化。这些能力与nestedHeaders是正交的嵌套表头负责分组标题setHeader负责单个数据列标题例如在Other Information分组下你依然可以随时把列头从 Food 改成 Food Category而嵌套分组的colspan布局不受影响。配置要点速查与常见误区colspan 必须与列数匹配每一层各单元格colspan之和应与该层实际覆盖的列数一致虽然组件不强制校验但失配会导致合并错位。可参照文档示例让顶层colspan等于minDimensions的列维度。hidden 列会自动补偿渲染时组件会把隐藏列计入单元格覆盖范围无需手动调整colspan。增删列只修正每行最后一个单元格新增/删除列时嵌套表头每行的最后一个分组会自动伸缩中间分组保持不变。导出嵌套表头需开启表头导出通过includeHeadersOnDownload配置或显式includeHeaders参数嵌套表头才会写入 CSV 的前几行。v4 与 v5 的配置位置不同v4 中nestedHeaders与data/columns平级v5 起放入worksheets[0]内。迁移旧代码时务必调整层级。延伸阅读列头基础配置title / tooltip / onchangeheader页脚行与公式汇总footersv4 嵌套表头示例原文列相关的动态操作插入、删除、隐藏测试用例赞分享前端UI组件【免费下载链接】ceJspreadsheet is a lightweight JavaScript data grid component for creating interactive data grids with advanced spreadsheet controls.项目地址https://gitcode.com/gh_mirrors/ce/ce点击查看免费下载相关推荐Jspreadsheet 嵌套表头Nested Headers完整指南多级列头配置、框架集成示例与底层源码解析Jspreadsheet 嵌套表头Nested Headers完整指南多级列头配置、框架集成示例与底层源码解析 本篇技术指南聚焦 Jspreadsheet前端UI组件JspreadsheetJexcel表头完全指南nestedHeaders 嵌套表头与 setHeader/getHeader 编程式更新JspreadsheetJexcel表头完全指南nestedHeaders 嵌套表头与 setHeader/getHeader 编程式更新 导读 本指南围前端UI组件Jspreadsheet CE 嵌套表头终极指南构建专业级多层次数据结构Jspreadsheet CE 嵌套表头终极指南构建专业级多层次数据结构 在数据管理和展示领域Jspreadsheet CE 的嵌套表头功能为开发者和用户提前端UI组件上一篇精通ProperTree7个高效Plist编辑技巧与进阶实战指南下一篇视频文件突然损坏打不开3分钟学会用Untrunc抢救你的珍贵回忆创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考
返回列表