经验首页 前端设计 程序设计 Java相关 移动开发 数据库/运维 软件/图像 大数据/云计算 其他经验
当前位置:技术经验 » Java相关 » Spring Boot » 查看文章
Svelte框架实现表格协同文档
来源:cnblogs  作者:葡萄城技术团队  时间:2023/1/18 8:43:05  对本文有异议

首先,从框架搭建上,本篇示例采用当下流行的前后端分离的开发方式,前端使用npm作为脚手架搭建Svelte框架。 后端使用Java的SpringBoot作为后端框架。
首先,介绍下在前端Svelte框架下搭建在线表格编辑器。
1、在pageage.json文件中引入相关资源

  1. "@grapecity/spread-excelio": "15.2.5",
  2. "@grapecity/spread-sheets": "15.2.5",
  3. "@grapecity/spread-sheets-barcode": "15.2.5",
  4. "@grapecity/spread-sheets-charts": "15.2.5",
  5. "@grapecity/spread-sheets-designer": "15.2.5",
  6. "@grapecity/spread-sheets-designer-resources-cn": "15.2.5",
  7. "@grapecity/spread-sheets-languagepackages": "15.2.5",
  8. "@grapecity/spread-sheets-pdf": "15.2.5",
  9. "@grapecity/spread-sheets-pivot-addon": "15.2.5",
  10. "@grapecity/spread-sheets-pivots": "^14.0.0",
  11. "@grapecity/spread-sheets-print": "15.2.5",
  12. "@grapecity/spread-sheets-resources-zh": "15.2.5",
  13. "@grapecity/spread-sheets-shapes": "15.2.5",
  14. "@grapecity/spread-sheets-tablesheet": "15.2.5",

2、然后,集成在线表格编辑器Svelte组件版。在上一篇文章中,我们介绍了如何在Svelte框架中实现在线表格编辑器。
我们按照此思路新建一个SpreadSheet.svelte文件,写入基础在线表格编辑器。

  1. <script>
  2. import {onMount} from 'svelte';
  3. import '@grapecity/spread-sheets-print';
  4. import "@grapecity/spread-sheets-charts";
  5. import '@grapecity/spread-sheets-shapes';
  6. import '@grapecity/spread-sheets-pivot-addon';
  7. import '@grapecity/spread-sheets-tablesheet';
  8. import '@grapecity/spread-sheets-designer-resources-cn';
  9. import '@grapecity/spread-sheets-designer';
  10. import * as GC from '@grapecity/spread-sheets';
  11. import * as GCDesigner from '@grapecity/spread-sheets-designer';
  12. let designer = null;
  13. onMount(async () => {
  14. designer = new GCDesigner.Spread.Sheets.Designer.Designer(document.getElementById("designerHost"));
  15. let spread = designer.getWorkbook();
  16. });
  17. </script>
  18. <div id="designerHost" class="designer-host"></div>
  19. <style scoped>
  20. @import "@grapecity/spread-sheets-designer/styles/gc.spread.sheets.designer.min.css";
  21. @import '@grapecity/spread-sheets/styles/gc.spread.sheets.excel2013white.css';
  22. .designer-host {
  23. width: 100%;
  24. height: 100vh;
  25. }
  26. </style>

3、协同文档可能不止一个,我们需要在页面上创建一个文档列表,来允许用户选择编辑哪个文档,所以我们需要创建一个文档列表页面OnlineSheets.svelte。在此页面中,我们要实现路由跳转,和加载文档数据。
这里我们用了svelte-spa-router进行路由跳转 与isomorphic-fetch进行前后端数据传输。

  1. <script>
  2. import {onMount} from 'svelte';
  3. import { link } from "svelte-spa-router";
  4. import {Utility} from "../utility.js";
  5. let docList = [];
  6. onMount(async () => {
  7. Utility.getDocList().then(result => {
  8. docList = result.map((item,index)=>{
  9. return {
  10. path:'/Spreadsheet/' + item.substring(0, item.lastIndexOf('.')),
  11. index,
  12. fileName:item
  13. }
  14. })
  15. });
  16. });
  17. </script>
  18. <main class="main">
  19. <table className='table' aria-labelledby="tabelLabel">
  20. <thead>
  21. <tr>
  22. <th>Document</th>
  23. <th></th>
  24. </tr>
  25. </thead>
  26. <tbody>
  27. {#each docList as docItem}
  28. <tr>
  29. <td>{docItem.index}</td>
  30. <td>{docItem.fileName}</td>
  31. <td className='row'>
  32. <a use:link={docItem.path}> Open</a>
  33. </td>
  34. </tr>
  35. {/each}
  36. </tbody>
  37. </table>
  38. </main>

以上代码实现了文档列表查看与文档跳转,使用 Open将跳转至前面设计好的在线表格编辑器中。
至此,前端的相关内容就准备好了,接下来搭建下后端工作。
后端的准备工作,首先安装gradle作为包管理器。当然,这里也可以用其他工具来代替,例如maven,或者源生引入jar包的方式将需要用到的jar包引入进来。之后创建springboot工程配合搭建gradle引用GCExcel以及后面协同需要用到的websocket。

  1. <dependencies>
  2. <dependency>
  3. <groupId>org.springframework.boot</groupId>
  4. <artifactId>spring-boot-starter-web</artifactId>
  5. </dependency>
  6. <dependency>
  7. <groupId>org.springframework.boot</groupId>
  8. <artifactId>spring-boot-starter-test</artifactId>
  9. <scope>test</scope>
  10. </dependency>
  11. <dependency>
  12. <groupId>org.springframework.boot</groupId>
  13. <artifactId>spring-boot-starter-tomcat</artifactId>
  14. <version>2.4.3</version>
  15. </dependency>
  16. <dependency>
  17. <groupId>org.springframework.boot</groupId>
  18. <artifactId>spring-boot-starter-websocket</artifactId>
  19. <version>2.4.3</version>
  20. </dependency>
  21. <dependency>
  22. <groupId>com.grapecity.documents</groupId>
  23. <artifactId>gcexcel</artifactId>
  24. <version>4.0.3</version>
  25. </dependency>
  26. <dependency>
  27. <groupId>com.google.code.gson</groupId>
  28. <artifactId>gson</artifactId>
  29. <version>2.8.6</version>
  30. </dependency>
  31. <dependency>
  32. <groupId>javax.servlet</groupId>
  33. <artifactId>jstl</artifactId>
  34. <version>1.2</version>
  35. </dependency>
  36. <dependency>
  37. <groupId>org.apache.tomcat.embed</groupId>
  38. <artifactId>tomcat-embed-jasper</artifactId>
  39. <version>10.0.2</version>
  40. </dependency>
  41. <dependency>
  42. <groupId>com.jayway.jsonpath</groupId>
  43. <artifactId>json-path</artifactId>
  44. <version>2.5.0</version>
  45. </dependency>
  46. </dependencies>

这样子,我们做了框架的基本环境搭建,接下来我们介绍下如何搭建webSocket。
在SpreadSheet.svelte文件中写入如下代码建立webSocket链接:

  1. function connectDocument(docName) {
  2. if (webSocket != null) {
  3. return;
  4. }
  5. var ws = new WebSocket(Utility.webSocketUrl); //'ws://localhost:8090/spreadjs'
  6. ws.onopen = function () {
  7. var data = {
  8. cmd: "connect",
  9. docID: docName
  10. }
  11. ws.send(JSON.stringify(data));
  12. }
  13. ws.onmessage = onmessage;
  14. webSocket = ws;
  15. }

接下来我们访问下文档列表页,从文档列表页跳转进入文档,进行编辑。

接下来我们需要监听前端发出的操作。这里因为在线表格编辑器本身将所有用户可能做的操作全部做了封装,所以省下了很多的功夫。

  1. onMount(async () => {
  2. //初始化Designer
  3. designer = new GCDesigner.Spread.Sheets.Designer.Designer(document.getElementById("designerHost"));
  4. let spread = designer.getWorkbook();
  5. //fromJSON
  6. openDocument(docName);
  7. //建立webSocket
  8. connectDocument(docName);
  9. var cm = spread.commandManager();
  10. cm.addListener('myListener', onCommandExecute)
  11. });

根据cmd去判断并且对命令再做一些简单封装,之后将封装过的命令发到服务端,之后通过websocket发同步指令:

  1. function onCommandExecute(args) {
  2. console.log(args.command);
  3. var command = args.command;
  4. var ServerCommand = null;
  5. switch (command.cmd) {
  6. case Utility.ServerCommands.EditCell:
  7. ServerCommand = {
  8. sheetName: command.sheetName,
  9. row: command.row,
  10. column: command.col,
  11. newValue: command.newValue
  12. }
  13. break;
  14. case Utility.ServerCommands.ResizeRow:
  15. ServerCommand = {
  16. sheetName: command.sheetName,
  17. rows: command.rows,
  18. size: command.size
  19. };
  20. break;
  21. case Utility.ServerCommands.ResizeColumn:
  22. ServerCommand = {
  23. sheetName: command.sheetName,
  24. columns: command.columns,
  25. size: command.size
  26. };
  27. break;
  28. case 'Designer.' + Utility.ServerCommands.SetFontFamily:
  29. case 'Designer.' + Utility.ServerCommands.SetFontSize:
  30. case 'Designer.' + Utility.ServerCommands.SetBackColor:
  31. case 'Designer.' + Utility.ServerCommands.SetForeColor:
  32. case 'Designer.' + Utility.ServerCommands.SetFontWeight:
  33. case 'Designer.' + Utility.ServerCommands.SetFontStyle:
  34. case 'Designer.' + Utility.ServerCommands.SetUnderline:
  35. case 'Designer.' + Utility.ServerCommands.SetDoubleUnderline:
  36. if (command.value && command.value.indexOf('undefined') === -1) {
  37. ServerCommand = {
  38. sheetName: command.sheetName,
  39. selections: command.selections,
  40. value: command.value
  41. }
  42. }
  43. break;
  44. case Utility.ServerCommands.MoveFloatingObjects:
  45. ServerCommand = {
  46. sheetName: command.sheetName,
  47. floatingObjects: command.floatingObjects,
  48. offsetX: command.offsetX,
  49. offsetY: command.offsetY
  50. };
  51. break;
  52. case Utility.ServerCommands.ResizeFloatingObjects:
  53. ServerCommand = {
  54. sheetName: command.sheetName,
  55. floatingObjects: command.floatingObjects,
  56. offsetX: command.offsetX,
  57. offsetY: command.offsetY,
  58. offsetWidth: command.offsetWidth,
  59. offsetHeight: command.offsetHeight
  60. };
  61. break;
  62. case Utility.ServerCommands.InsertColumns:
  63. case Utility.ServerCommands.InsertRows:
  64. ServerCommand = {
  65. sheetName: command.sheetName,
  66. selections: command.selections
  67. };
  68. break;
  69. default:
  70. }
  71. if (ServerCommand != null) {
  72. var cmd = command.cmd;
  73. var dotIndex = cmd.lastIndexOf('.');
  74. if (dotIndex !== -1) {
  75. cmd = cmd.substring(dotIndex + 1);
  76. }
  77. ServerCommand.cmd = cmd;
  78. ServerCommand.docID = params.fileName;
  79. Utility.ExecuteCommandAtServer(ServerCommand);
  80. command.docID = ServerCommand.docID;
  81. webSocket.send(JSON.stringify(command))
  82. }
  83. }

当协同端通过websocket接收到请求的时候,使用onmessage方法做同步命令。这里在协同端执行command之前需要先撤销之前的监听,避免再发送websocket导致死循环。在执行之后,再次添加监听。

  1. function onmessage(message) {
  2. var command = JSON.parse(message.data);
  3. command._styles = null;
  4. let spread = designer.getWorkbook()
  5. var cm = spread.commandManager();
  6. cm.removeListener('myListener');
  7. spread.commandManager().execute(command);
  8. cm.addListener('myListener', onCommandExecute);
  9. }

至此,协同基础内容搭建结束,我们来看看编辑单元格内容后,发生了什么吧。
如下图所示,修改E4单元格内容,同时打开控制台网络tab。
将E4单元格数值2500改为2000,此时触发了EditCell事件,同时发出了交互指令:

此时新建一个窗口,复制链接,查看文档内容已经变为了2000。
如下动图所示:

拓展阅读

React + Springboot + Quartz,从0实现Excel报表自动化

电子表格也能做购物车?简单三步就能实现

使用纯前端类Excel表格控件SpreadJS构建企业现金流量表

原文链接:https://www.cnblogs.com/powertoolsteam/p/17057838.html

 友情链接:直通硅谷  点职佳  北美留学生论坛

本站QQ群:前端 618073944 | Java 606181507 | Python 626812652 | C/C++ 612253063 | 微信 634508462 | 苹果 692586424 | C#/.net 182808419 | PHP 305140648 | 运维 608723728

W3xue 的所有内容仅供测试,对任何法律问题及风险不承担任何责任。通过使用本站内容随之而来的风险与本站无关。
关于我们  |  意见建议  |  捐助我们  |  报错有奖  |  广告合作、友情链接(目前9元/月)请联系QQ:27243702 沸活量
皖ICP备17017327号-2 皖公网安备34020702000426号