From 07db9ae60ded485e239568a5ddb758cbcb99db05 Mon Sep 17 00:00:00 2001
From: YEL!ne <1638317920@qq.com>
Date: Tue, 24 Sep 2024 17:26:43 +0800
Subject: [PATCH] feat: add configuration and live demo for ArcoVue as Editor
---
common/config/rush/pnpm-lock.yaml | 4 +-
.../en/edit-data/arco-select-editor.md | 220 +++++++++++++++++-
.../zh/edit-data/arco-select-editor.md | 212 ++++++++++++++++-
docs/package.json | 1 +
docs/src/main.tsx | 3 +
5 files changed, 431 insertions(+), 9 deletions(-)
diff --git a/common/config/rush/pnpm-lock.yaml b/common/config/rush/pnpm-lock.yaml
index db8c76bb9..cc3120d27 100644
--- a/common/config/rush/pnpm-lock.yaml
+++ b/common/config/rush/pnpm-lock.yaml
@@ -8,6 +8,7 @@ importers:
../../docs:
specifiers:
'@arco-design/web-react': 2.60.2
+ '@arco-design/web-vue': ^2.11.0
'@internal/eslint-config': workspace:*
'@internal/ts-config': workspace:*
'@types/buble': ^0.20.5
@@ -47,6 +48,7 @@ importers:
yargs: ^17.1.1
dependencies:
'@arco-design/web-react': 2.60.2_52ux7kpa62vlx2is4pxiuz7b44
+ '@arco-design/web-vue': 2.56.1_vue@3.5.0
'@visactor/openinula-vtable': link:../packages/openinula-vtable
'@visactor/react-vtable': link:../packages/react-vtable
'@visactor/vchart': 1.12.1
@@ -1130,7 +1132,6 @@ packages:
resize-observer-polyfill: 1.5.1
scroll-into-view-if-needed: 2.2.31
vue: 3.5.0_typescript@4.9.5
- dev: true
/@babel/code-frame/7.24.7:
resolution: {integrity: sha512-BcYH1CVJBO9tvyIZ2jVeXgSIMvGZ2FDRvDdOIVQyuklNKSsx+eppDEBq/g47Ayw+RqNFE+URvOShmf+f/qwAlA==}
@@ -12374,7 +12375,6 @@ packages:
resolution: {integrity: sha512-dGCXy99wZQivjmjIqihaBQNjryrz5rueJY7eHfTdyWEiR4ttYpsajb14rn9s5d4DY4EcY6+4+U/maARBXJedkA==}
dependencies:
compute-scroll-into-view: 1.0.20
- dev: true
/semver-compare/1.0.0:
resolution: {integrity: sha512-YM3/ITh2MJ5MtzaM429anh+x2jiLVjqILF4m4oyQB18W7Ggea7BfqdH/wGMK7dDiMghv/6WG7znWMwUDzJiXow==}
diff --git a/docs/assets/demo-vue/en/edit-data/arco-select-editor.md b/docs/assets/demo-vue/en/edit-data/arco-select-editor.md
index 51580888d..a42d60e31 100644
--- a/docs/assets/demo-vue/en/edit-data/arco-select-editor.md
+++ b/docs/assets/demo-vue/en/edit-data/arco-select-editor.md
@@ -1,21 +1,229 @@
---
category: examples
group: functional-components
-title: 自定义编辑器中使用arco列表选择器
+title: Using Arco Select in Custom Editor
cover:
link: '../guide/Developer_Ecology/vue'
---
-# 自定义编辑器中使用 arco 列表选择器
+# Using Arco Select in Custom Editor
-创建自定义编辑器类 ArcoListEditor, 并实现 onStart 方法,创建一个 arco-design 的 Select 组件,并将组件挂载到编辑器容器中。完善 isEditorElement 和 onEnd 方法。
+Create a custom editor class `ArcoListEditor` and implement the `onStart` method to create an Arco Design `Select` component and mount it to the editor container. Complete the `isEditorElement` and `onEnd` methods.
-参考:
+References:
https://visactor.io/vtable/guide/edit/edit_cell
https://arco.design/vue/components/select
-## 代码演示
+## Code Demonstration
-```javascript livedemo template=vtable-vue
\ No newline at end of file
+```javascript livedemo template=vtable-vue
+
+class ArcoListEditor {
+ root = null;
+ element = null;
+ container = null;
+ currentValue = null;
+
+ onStart(editorContext) {
+ const { container, referencePosition, value } = editorContext;
+ this.container = container;
+ this.createElement(value);
+ if (value) this.setValue(value);
+ if (referencePosition?.rect) this.adjustPosition(referencePosition.rect);
+ }
+
+ createElement(defaultValue) {
+ const div = document.createElement('div');
+ div.style.position = 'absolute';
+ div.style.width = '100%';
+ div.style.padding = '1px';
+ div.style.boxSizing = 'border-box';
+ this.container?.appendChild(div);
+
+ const app = this.createVueApp(defaultValue);
+ app.mount(div);
+ this.root = app;
+ this.element = div;
+ }
+
+ createVueApp(defaultValue) {
+ const self = this;
+ return createApp({
+ data() {
+ return {
+ currentValue: defaultValue,
+ options: ['Beijing', 'Shanghai', 'Guangzhou'],
+ };
+ },
+ render() {
+ return h('div', {}, [
+ h(ArcoDesignVue.Select, {
+ style: { height: '32px' },
+ placeholder: 'Select city',
+ modelValue: this.currentValue,
+ 'onUpdate:modelValue': (value) => {
+ this.currentValue = value;
+ self.setValue(value);
+ },
+ }, {
+ default: () =>
+ this.options.map((option) =>
+ h(ArcoDesignVue.Option, { key: option, value: option }, { default: () => option })
+ ),
+ }),
+ ]);
+ },
+ });
+ }
+
+ getValue() {
+ return this.currentValue;
+ }
+
+ setValue(value) {
+ this.currentValue = value;
+ }
+
+ adjustPosition(rect) {
+ if (this.element) {
+ this.element.style.top = `${rect.top}px`;
+ this.element.style.left = `${rect.left}px`;
+ this.element.style.width = `${rect.width}px`;
+ this.element.style.height = `${rect.height}px`;
+ }
+ }
+
+ onEnd() {
+ if (this.root) {
+ this.root.unmount();
+ this.root = null;
+ }
+ if (this.element && this.container) {
+ this.container.removeChild(this.element);
+ this.element = null;
+ }
+ }
+
+ isEditorElement(target) {
+ return this.element?.contains(target) || this.isClickPopUp(target);
+ }
+
+ isClickPopUp(target) {
+ while (target) {
+ if (target.classList && target.classList.contains('arco-select')) {
+ return true;
+ }
+ target = target.parentNode;
+ }
+ return false;
+ }
+}
+
+const input_editor = new VTable_editors.InputEditor();
+const date_input_editor = new VTable_editors.DateInputEditor();
+VTable.register.editor('input-editor', input_editor);
+VTable.register.editor('date-input-editor', date_input_editor);
+VTable.register.editor('arcoVue-editor', new ArcoListEditor());
+
+function generateRandomString(length) {
+ let result = '';
+ const characters = 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz';
+ for (let i = 0; i < length; i++) {
+ result += characters.charAt(Math.floor(Math.random() * characters.length));
+ }
+ return result;
+}
+
+const generatePersons = (count) => {
+ return Array.from(new Array(count)).map((_, i) => {
+ const first = generateRandomString(10);
+ const last = generateRandomString(4);
+ return {
+ id: i + 1,
+ email1: `${first}_${last}@xxx.com`,
+ name: first,
+ lastName: last,
+ address: `No.${i + 100} ${generateRandomString(10)} ${generateRandomString(5)} ${generateRandomString(5)}`,
+ sex: i % 2 === 0 ? 'boy' : 'girl',
+ work: i % 2 === 0 ? 'back-end engineer' : 'front-end engineer',
+ city: 'beijing',
+ };
+ });
+};
+
+const records = generatePersons(10);
+const columns = [
+ {
+ field: 'id',
+ title: 'ID',
+ width: 80,
+ sort: true,
+ },
+ {
+ field: 'full name',
+ title: 'Full name',
+ columns: [
+ {
+ field: 'name',
+ title: 'First Name\n(input editor)',
+ width: 140,
+ editor: 'input-editor',
+ },
+ {
+ field: 'lastName',
+ title: 'Last Name\n(input editor)',
+ width: 100,
+ editor: 'input-editor',
+ },
+ ],
+ },
+ {
+ field: 'address',
+ title: 'location\n(arcoVue-editor)',
+ width: 400,
+ editor: 'arcoVue-editor',
+ },
+];
+
+const option = {
+ enableLineBreak: true,
+ autoWrapText: true,
+ limitMaxAutoWidth: 700,
+ heightMode: 'autoHeight',
+ editCellTrigger: 'click',
+ keyboardOptions: {
+ copySelected: true,
+ pasteValueToCell: true,
+ selectAllOnCtrlA: true,
+ },
+};
+
+const app = createApp({
+ template: `
+
+
+
+ `,
+ data() {
+ return {
+ records,
+ columns,
+ option,
+ };
+ },
+});
+
+app.component('ListTable', VueVTable.ListTable);
+app.component('ListColumn', VueVTable.ListColumn);
+
+app.mount(`#${CONTAINER_ID}`);
diff --git a/docs/assets/demo-vue/zh/edit-data/arco-select-editor.md b/docs/assets/demo-vue/zh/edit-data/arco-select-editor.md
index 51580888d..49c445454 100644
--- a/docs/assets/demo-vue/zh/edit-data/arco-select-editor.md
+++ b/docs/assets/demo-vue/zh/edit-data/arco-select-editor.md
@@ -18,4 +18,214 @@ https://arco.design/vue/components/select
## 代码演示
-```javascript livedemo template=vtable-vue
\ No newline at end of file
+```javascript livedemo template=vtable-vue
+
+
+class ArcoListEditor {
+ root = null;
+ element = null;
+ container = null;
+ currentValue = null;
+
+ onStart(editorContext) {
+ const { container, referencePosition, value } = editorContext;
+ this.container = container;
+ this.createElement(value);
+ if (value) this.setValue(value);
+ if (referencePosition?.rect) this.adjustPosition(referencePosition.rect);
+ }
+
+ createElement(defaultValue) {
+ const div = document.createElement('div');
+ div.style.position = 'absolute';
+ div.style.width = '100%';
+ div.style.padding = '1px';
+ div.style.boxSizing = 'border-box';
+ this.container?.appendChild(div);
+
+ const app = this.createVueApp(defaultValue);
+ app.mount(div);
+ this.root = app;
+ this.element = div;
+ }
+
+ createVueApp(defaultValue) {
+ const self = this;
+ return createApp({
+ data() {
+ return {
+ currentValue: defaultValue,
+ options: ['Beijing', 'Shanghai', 'Guangzhou'],
+ };
+ },
+ render() {
+ return h('div', {}, [
+ h(ArcoDesignVue.Select, {
+ style: { height: '32px' },
+ placeholder: 'Select city',
+ modelValue: this.currentValue,
+ 'onUpdate:modelValue': (value) => {
+ this.currentValue = value;
+ self.setValue(value);
+ },
+ }, {
+ default: () =>
+ this.options.map((option) =>
+ h(ArcoDesignVue.Option, { key: option, value: option }, { default: () => option })
+ ),
+ }),
+ ]);
+ },
+ });
+ }
+
+ getValue() {
+ return this.currentValue;
+ }
+
+ setValue(value) {
+ this.currentValue = value;
+ }
+
+ adjustPosition(rect) {
+ if (this.element) {
+ this.element.style.top = `${rect.top}px`;
+ this.element.style.left = `${rect.left}px`;
+ this.element.style.width = `${rect.width}px`;
+ this.element.style.height = `${rect.height}px`;
+ }
+ }
+
+ onEnd() {
+ if (this.root) {
+ this.root.unmount();
+ this.root = null;
+ }
+ if (this.element && this.container) {
+ this.container.removeChild(this.element);
+ this.element = null;
+ }
+ }
+
+ isEditorElement(target) {
+ return this.element?.contains(target) || this.isClickPopUp(target);
+ }
+
+ isClickPopUp(target) {
+ while (target) {
+ if (target.classList && target.classList.contains('arco-select')) {
+ return true;
+ }
+ target = target.parentNode;
+ }
+ return false;
+ }
+}
+
+const input_editor = new VTable_editors.InputEditor();
+const date_input_editor = new VTable_editors.DateInputEditor();
+VTable.register.editor('input-editor', input_editor);
+VTable.register.editor('date-input-editor', date_input_editor);
+VTable.register.editor('arcoVue-editor', new ArcoListEditor());
+
+function generateRandomString(length) {
+ let result = '';
+ const characters = 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz';
+ for (let i = 0; i < length; i++) {
+ result += characters.charAt(Math.floor(Math.random() * characters.length));
+ }
+ return result;
+}
+
+const generatePersons = (count) => {
+ return Array.from(new Array(count)).map((_, i) => {
+ const first = generateRandomString(10);
+ const last = generateRandomString(4);
+ return {
+ id: i + 1,
+ email1: `${first}_${last}@xxx.com`,
+ name: first,
+ lastName: last,
+ address: `No.${i + 100} ${generateRandomString(10)} ${generateRandomString(5)} ${generateRandomString(5)}`,
+ sex: i % 2 === 0 ? 'boy' : 'girl',
+ work: i % 2 === 0 ? 'back-end engineer' : 'front-end engineer',
+ city: 'beijing',
+ };
+ });
+};
+
+const records = generatePersons(10);
+const columns = [
+ {
+ field: 'id',
+ title: 'ID',
+ width: 80,
+ sort: true,
+ },
+ {
+ field: 'full name',
+ title: 'Full name',
+ columns: [
+ {
+ field: 'name',
+ title: 'First Name\n(input editor)',
+ width: 140,
+ editor: 'input-editor',
+ },
+ {
+ field: 'lastName',
+ title: 'Last Name\n(input editor)',
+ width: 100,
+ editor: 'input-editor',
+ },
+ ],
+ },
+ {
+ field: 'address',
+ title: 'location\n(arcoVue-editor)',
+ width: 400,
+ editor: 'arcoVue-editor',
+ },
+];
+
+const option = {
+ enableLineBreak: true,
+ autoWrapText: true,
+ limitMaxAutoWidth: 700,
+ heightMode: 'autoHeight',
+ editCellTrigger: 'click',
+ keyboardOptions: {
+ copySelected: true,
+ pasteValueToCell: true,
+ selectAllOnCtrlA: true,
+ },
+};
+
+const app = createApp({
+ template: `
+
+
+
+ `,
+ data() {
+ return {
+ records,
+ columns,
+ option,
+ };
+ },
+});
+
+
+app.component('ListTable', VueVTable.ListTable);
+app.component('ListColumn', VueVTable.ListColumn);
+
+app.mount(`#${CONTAINER_ID}`);
diff --git a/docs/package.json b/docs/package.json
index ced94c107..d49cb5625 100644
--- a/docs/package.json
+++ b/docs/package.json
@@ -11,6 +11,7 @@
},
"dependencies": {
"@arco-design/web-react": "2.60.2",
+ "@arco-design/web-vue": "^2.11.0",
"@visactor/vtable": "workspace:*",
"@visactor/react-vtable": "workspace:*",
"@visactor/vue-vtable": "workspace:*",
diff --git a/docs/src/main.tsx b/docs/src/main.tsx
index 7f73a95e7..aaf774b94 100644
--- a/docs/src/main.tsx
+++ b/docs/src/main.tsx
@@ -13,11 +13,14 @@ import * as VueVTable from '@visactor/vue-vtable';
import * as InulaVTable from '@visactor/openinula-vtable';
import { App } from './app';
import * as ArcoDesign from '@arco-design/web-react';
+import * as ArcoDesignVue from '@arco-design/web-vue';
import * as ArcoDesignIcon from '@arco-design/web-react/icon';
import '@arco-design/web-react/dist/css/arco.css';
+import '@arco-design/web-vue/dist/arco.css';
import { createApp, ref, onMounted, h } from 'vue';
(window as any).ArcoDesign = ArcoDesign;
+(window as any).ArcoDesignVue = ArcoDesignVue;
(window as any).ArcoDesignIcon = ArcoDesignIcon;
(window as any).VTable = VTable;
(window as any).VRender = VRender;