You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何借助SpreadJS与OfficeJS将xlsm文件加载至现有Excel工作簿?

实现方案:用SpreadJS转xlsm为JSON后通过OfficeJS导入Excel Web加载项

核心思路

完全可以借助SpreadJS实现需求:先通过SpreadJS读取本地xlsm文件并导出为SSJSON格式(SpreadJS的标准JSON结构),然后解析该JSON提取工作表的单元格数据、格式信息,最后调用OfficeJS API在现有工作簿中创建新工作表并写入内容。

步骤及代码实现

1. 完善SpreadJS的导入与导出逻辑

修改现有代码,在SpreadJS成功导入xlsm后,将其导出为SSJSON并触发OfficeJS导入流程:

this.spread = new GC.Spread.Sheets.Workbook("");

selectedFileChange(e: any) {
    this.selectedFile = e.target.files[0];
    this.openFileType = this.getFileType(this.selectedFile);
    this.open();
}

getFileType(file: File) {
    if (!file) return;
    const extensionName = file.name.substring(file.name.lastIndexOf(".") + 1);
    if (extensionName === 'sjs') return 'sjs';
    if (['xlsx', 'xlsm'].includes(extensionName)) return 'xlsx';
    if (['ssjson', 'json'].includes(extensionName)) return 'ssjson';
    if (extensionName === 'csv') return 'csv';
}

open() {
    const file = this.selectedFile;
    if (!file) return;

    const fileType = this.getFileType(file);
    const options = this.getOptions('open');

    const successCallback = () => {
        // 导入成功后导出为SSJSON
        const ssJson = this.spread.toJSON();
        // 调用OfficeJS导入逻辑
        this.importToExcelViaOfficeJS(ssJson);
    };

    const errorCallback = (e: any) => {
        console.error('文件导入失败:', e);
    };

    if (fileType === 'sjs') {
        this.spread.open(file, successCallback, errorCallback, options);
    } else {
        this.spread.import(file, successCallback, errorCallback);
    }
}

2. 解析SSJSON并通过OfficeJS写入新工作表

新增方法解析SpreadJS导出的JSON,提取工作表内容并通过OfficeJS创建新工作表:

async importToExcelViaOfficeJS(ssJson: any) {
    try {
        await Excel.run(async (context) => {
            // 获取当前工作簿
            const workbook = context.workbook;
            // 提取SpreadJS中的第一个工作表数据(多表可循环处理)
            const spreadSheet = ssJson.sheets[0];
            const sheetName = spreadSheet.name || '导入的工作表';
            
            // 创建新工作表
            const newSheet = workbook.worksheets.add(sheetName);
            newSheet.activate();

            // 提取单元格数据范围
            const rows = spreadSheet.rows;
            if (!rows || rows.length === 0) return;

            // 确定最大行和列数
            const maxRow = rows.length;
            let maxCol = 0;
            rows.forEach((row: any) => {
                if (row.cells) {
                    row.cells.forEach((cell: any) => {
                        if (cell.col > maxCol) maxCol = cell.col;
                    });
                }
            });

            // 准备数据数组
            const dataArray = Array(maxRow).fill(null).map(() => Array(maxCol + 1).fill(null));
            
            // 填充数据并记录需要设置格式的单元格
            const formatCells: Array<{range: Excel.Range, format: string}> = [];
            rows.forEach((row: any, rowIdx: number) => {
                if (row.cells) {
                    row.cells.forEach((cell: any) => {
                        const colIdx = cell.col;
                        // 设置单元格值
                        dataArray[rowIdx][colIdx] = cell.v;
                        // 记录单元格数字格式(可扩展字体、对齐等格式)
                        if (cell.f) {
                            const range = newSheet.getRange(rowIdx + 1, colIdx + 1, 1, 1);
                            formatCells.push({range, format: cell.f});
                        }
                    });
                }
            });

            // 批量写入数据
            const targetRange = newSheet.getRange(1, 1, maxRow, maxCol + 1);
            targetRange.values = dataArray;

            // 批量设置单元格格式
            formatCells.forEach(item => {
                item.range.numberFormat = item.format;
            });

            await context.sync();
            console.log('工作表导入成功');
        });
    } catch (error) {
        console.error('OfficeJS操作失败:', error);
    }
}

注意事项

  • 宏处理:xlsm文件中的宏无法通过此方式导入,OfficeJS加载项不支持直接运行或导入VBA宏,此方案仅导入工作表的单元格数据和格式。
  • 格式兼容性:SpreadJS的格式与Excel的格式大部分兼容,但部分特殊格式(如条件格式)可能需要额外适配,可根据需求扩展格式处理逻辑。
  • 性能优化:如果导入的工作表数据量较大,建议分批次写入数据,避免OfficeJS同步时出现性能瓶颈。

内容的提问来源于stack exchange,提问作者WorksOnMyLocal

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.10 00:40:18