找回密码
 立即注册

QQ登录

只需一步,快速开始

dexteryao 讲师达人认证 悬赏达人认证 SpreadJS 开发认证

超级版主

124

主题

8928

帖子

1万

积分

超级版主

Rank: 8Rank: 8

积分
13548

讲师达人悬赏达人元老葡萄SpreadJS 认证SpreadJS 高级认证微信认证勋章

dexteryao 讲师达人认证 悬赏达人认证 SpreadJS 开发认证
超级版主   /  发表于:2021-9-22 18:07  /   查看:4091  /  回复:15
本帖最后由 dexteryao 于 2022-1-10 15:26 编辑

前一篇通过设置runtimeCompiler为true,动态编译组件让SpreadJS支持了动态创建VUE组件。

但是实际场景我们可能只需要动态创建VUE组件,而组件的template内容并需要动态。其实autoComplete也属于这种场景。
那我们就可以将动态创建的Component固化,按需import 然后挂载即可。这样就不需要开启runtimeCompiler了

具体做法
1. 封装AutoComplete组件封装的组件,需要注意一下几点
  • 组件提供text(或者value)属性,用于对应单元格需要编辑的值,组件中如果不是用model双向绑定,操作后需要主动更新text
  • 提供cellStyle,用户CellType根据单元格大小控制组件的大小
  • 组件如果有注入的DOM元素不在template div内部,需要添加gcUIElement属性,原因在上一篇有说明

  1. <template>
  2.   <div>
  3.     <el-autocomplete
  4.       :style="cellStyle"
  5.       popper-class="my-autocomplete"
  6.       v-model="text"
  7.       :fetch-suggestions="querySearch"
  8.       placeholder="请输入内容"
  9.       :popper-append-to-body="false"
  10.       value-key="name"
  11.       @select="handleSelect"
  12.     >
  13.       <i
  14.         class="el-icon-edit el-input__icon"
  15.         slot="suffix"
  16.         @click="handleIconClick"
  17.       >
  18.       </i>
  19.       <template slot-scope="{ item }">
  20.         <div class="name">{{ item.name }}</div>
  21.         <span class="addr">{{ item.phone }}</span>
  22.       </template>
  23.     </el-autocomplete>
  24.   </div>
  25. </template>
  26.   <script>

  27. import DataService from '../static/dataService'

  28. export default {
  29.     props: ['text','cellStyle'],
  30.     mounted() {
  31.         this.items = DataService.getEmployeesData();
  32.     },
  33.     methods: {
  34.         querySearch(queryString, cb) {
  35.             var items = this.items;
  36.             var results = queryString ? items.filter(this.createFilter(queryString)) : items;
  37.             // 无法设置动态内容的位置,可以动态添加gcUIElement
  38.             // setTimeout(() => {
  39.             //   let popDiv = document.getElementsByClassName("my-autocomplete")[0];
  40.             //   if(popDiv){
  41.             //     popDiv.setAttribute("gcUIElement", "gcEditingInput");
  42.             //   }
  43.             // }, 500);
  44.             // 调用 callback 返回建议列表的数据
  45.             cb(results);
  46.         },
  47.         createFilter(queryString) {
  48.             return (restaurant) => {
  49.             return (restaurant.name.toLowerCase().indexOf(queryString.toLowerCase()) === 0);
  50.             };
  51.         },
  52.         handleSelect(item) {
  53.             console.log(item);
  54.         },
  55.         handleIconClick(ev) {
  56.             console.log(ev);
  57.         }
  58.     }
  59. }
  60. </script>
复制代码
2 .autoCompleteCellType直接挂在组件,不需要动态声明了
  1. import AutoComplete from '../components/AutoComplete'
复制代码
  1. AutoComplateCellType.prototype.activateEditor = function (editorContext, cellStyle, cellRect, context) {
  2.     let width = cellRect.width > 180 ? cellRect.width : 180;
  3.     if (editorContext) {
  4.        // create component constructor
  5.        const AutoCompleteCtor = Vue.extend(AutoComplete);
  6.         this.vm = new AutoCompleteCtor({
  7.         propsData: {
  8.           cellStyle: {width: width+"px"}
  9.         }
  10.       }).$mount(editorContext.firstChild);
  11.     }
  12. };
复制代码



其余代码不变,参考前一篇文章,这样不仅不需要runtimeCompiler,代码可维护行也提高了。




15 个回复

正序浏览
dexteryao讲师达人认证 悬赏达人认证 SpreadJS 开发认证
超级版主   /  发表于:2023-12-12 16:25:41
16#
BattleHawk76 发表于 2023-12-12 15:47
怎么让第三方组件自动聚焦啊?

重写focus 方法,在方法中调用第三方组件的focus相关接口。因为第三方组件被封装了。可以得看情况从vm暴露一些接口出来

还有个简单的办法。在组件中,加载完成后用setTimeout 来延时,然后调用他自己的focus方法。
回复 使用道具 举报
BattleHawk76
注册会员   /  发表于:2023-12-12 15:47:44
15#
怎么让第三方组件自动聚焦啊?
回复 使用道具 举报
Joestar.XuSpreadJS 开发认证
超级版主   /  发表于:2023-11-22 17:29:17
14#
SpreadJS 17.0.9 | GcExcel 7.1.2 已发布~
回复 使用道具 举报
BattleHawk76
注册会员   /  发表于:2023-11-22 09:08:41
13#
孙志强 发表于 2023-7-19 10:24
大概流程是:activateEditor激活了,将放置在#gcEditingInput下的自定义组件显示,并将当前的值传递到组 ...

你好,能提供demo文件给我们参考一下吗?
回复 使用道具 举报
Joestar.XuSpreadJS 开发认证
超级版主   /  发表于:2023-10-25 16:37:02
12#
抓紧学习 发表于 2023-10-25 13:41
有完整的vue3实现的demo么

您好,目前还没有vue3的demo,您可以参考上述思路自行实现一下。
SpreadJS 17.0.9 | GcExcel 7.1.2 已发布~
回复 使用道具 举报
抓紧学习
注册会员   /  发表于:2023-10-25 13:41:14
11#
有完整的vue3实现的demo么
回复 使用道具 举报
Lynn.Dou讲师达人认证 悬赏达人认证 SpreadJS 开发认证
超级版主   /  发表于:2023-7-19 18:35:10
10#
孙志强 发表于 2023-7-19 10:24
大概流程是:activateEditor激活了,将放置在#gcEditingInput下的自定义组件显示,并将当前的值传递到组 ...

感谢分享,给您送上金币奖励
回复 使用道具 举报
孙志强讲师达人认证
金牌服务用户   /  发表于:2023-7-19 10:24:15
9#
本帖最后由 孙志强 于 2023-7-19 10:36 编辑
Joestar.Xu 发表于 2023-7-18 15:17
您好,您是如何实现的呢?能否提供一下您的代码,让大家一起学习学习

大概流程是:activateEditor激活了,将放置在#gcEditingInput下的自定义组件显示,并将当前的值传递到组件中,修改完毕后在getEditorValue返回组件的值,然后在deactivateEditor里隐藏组件
image.png837668762.png
image.png937097778.png

评分

参与人数 1金币 +500 收起 理由
Lynn.Dou + 500 很给力!

查看全部评分

回复 使用道具 举报
Joestar.XuSpreadJS 开发认证
超级版主   /  发表于:2023-7-18 15:17:01
8#
孙志强 发表于 2023-7-18 11:42
实现了,我做了一些改造,直接使用组件挂载到#gcEditingInput下更方便

您好,您是如何实现的呢?能否提供一下您的代码,让大家一起学习学习
SpreadJS 17.0.9 | GcExcel 7.1.2 已发布~
回复 使用道具 举报
12下一页
您需要登录后才可以回帖 登录 | 立即注册
返回顶部