add code
30
.gitignore
vendored
Normal file
|
@ -0,0 +1,30 @@
|
||||||
|
# Logs
|
||||||
|
logs
|
||||||
|
*.log
|
||||||
|
npm-debug.log*
|
||||||
|
yarn-debug.log*
|
||||||
|
yarn-error.log*
|
||||||
|
pnpm-debug.log*
|
||||||
|
lerna-debug.log*
|
||||||
|
|
||||||
|
node_modules
|
||||||
|
.DS_Store
|
||||||
|
dist
|
||||||
|
dist-ssr
|
||||||
|
coverage
|
||||||
|
*.local
|
||||||
|
|
||||||
|
/cypress/videos/
|
||||||
|
/cypress/screenshots/
|
||||||
|
|
||||||
|
# Editor directories and files
|
||||||
|
.vscode/*
|
||||||
|
!.vscode/extensions.json
|
||||||
|
.idea
|
||||||
|
*.suo
|
||||||
|
*.ntvs*
|
||||||
|
*.njsproj
|
||||||
|
*.sln
|
||||||
|
*.sw?
|
||||||
|
|
||||||
|
*.tsbuildinfo
|
3
.vscode/extensions.json
vendored
Normal file
|
@ -0,0 +1,3 @@
|
||||||
|
{
|
||||||
|
"recommendations": ["Vue.volar"]
|
||||||
|
}
|
29
README.md
Normal file
|
@ -0,0 +1,29 @@
|
||||||
|
# wps
|
||||||
|
|
||||||
|
This template should help get you started developing with Vue 3 in Vite.
|
||||||
|
|
||||||
|
## Recommended IDE Setup
|
||||||
|
|
||||||
|
[VSCode](https://code.visualstudio.com/) + [Volar](https://marketplace.visualstudio.com/items?itemName=Vue.volar) (and disable Vetur).
|
||||||
|
|
||||||
|
## Customize configuration
|
||||||
|
|
||||||
|
See [Vite Configuration Reference](https://vitejs.dev/config/).
|
||||||
|
|
||||||
|
## Project Setup
|
||||||
|
|
||||||
|
```sh
|
||||||
|
npm install
|
||||||
|
```
|
||||||
|
|
||||||
|
### Compile and Hot-Reload for Development
|
||||||
|
|
||||||
|
```sh
|
||||||
|
npm run dev
|
||||||
|
```
|
||||||
|
|
||||||
|
### Compile and Minify for Production
|
||||||
|
|
||||||
|
```sh
|
||||||
|
npm run build
|
||||||
|
```
|
13
index.html
Normal file
|
@ -0,0 +1,13 @@
|
||||||
|
<!DOCTYPE html>
|
||||||
|
<html lang="en">
|
||||||
|
<head>
|
||||||
|
<meta charset="UTF-8">
|
||||||
|
<link rel="icon" href="/favicon.ico">
|
||||||
|
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||||
|
<title>Vite App</title>
|
||||||
|
</head>
|
||||||
|
<body>
|
||||||
|
<div id="app"></div>
|
||||||
|
<script type="module" src="/src/main.js"></script>
|
||||||
|
</body>
|
||||||
|
</html>
|
8
jsconfig.json
Normal file
|
@ -0,0 +1,8 @@
|
||||||
|
{
|
||||||
|
"compilerOptions": {
|
||||||
|
"paths": {
|
||||||
|
"@/*": ["./src/*"]
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"exclude": ["node_modules", "dist"]
|
||||||
|
}
|
1318
package-lock.json
generated
Normal file
23
package.json
Normal file
|
@ -0,0 +1,23 @@
|
||||||
|
{
|
||||||
|
"name": "wps",
|
||||||
|
"version": "0.0.0",
|
||||||
|
"private": true,
|
||||||
|
"type": "module",
|
||||||
|
"scripts": {
|
||||||
|
"dev": "vite",
|
||||||
|
"build": "vite build",
|
||||||
|
"preview": "vite preview"
|
||||||
|
},
|
||||||
|
"dependencies": {
|
||||||
|
"@hufe921/canvas-editor": "^0.9.81",
|
||||||
|
"axios": "^1.7.2",
|
||||||
|
"element-plus": "^2.7.5",
|
||||||
|
"vue": "^3.4.21",
|
||||||
|
"vue-axios": "^3.5.2",
|
||||||
|
"vue-router": "^4.3.3"
|
||||||
|
},
|
||||||
|
"devDependencies": {
|
||||||
|
"@vitejs/plugin-vue": "^5.0.4",
|
||||||
|
"vite": "^5.2.8"
|
||||||
|
}
|
||||||
|
}
|
BIN
public/favicon.ico
Normal file
After Width: | Height: | Size: 4.2 KiB |
1012
src/App.vue
Normal file
2197
src/Appaaa.vue
Normal file
86
src/assets/base.css
Normal file
|
@ -0,0 +1,86 @@
|
||||||
|
/* color palette from <https://github.com/vuejs/theme> */
|
||||||
|
:root {
|
||||||
|
--vt-c-white: #ffffff;
|
||||||
|
--vt-c-white-soft: #f8f8f8;
|
||||||
|
--vt-c-white-mute: #f2f2f2;
|
||||||
|
|
||||||
|
--vt-c-black: #181818;
|
||||||
|
--vt-c-black-soft: #222222;
|
||||||
|
--vt-c-black-mute: #282828;
|
||||||
|
|
||||||
|
--vt-c-indigo: #2c3e50;
|
||||||
|
|
||||||
|
--vt-c-divider-light-1: rgba(60, 60, 60, 0.29);
|
||||||
|
--vt-c-divider-light-2: rgba(60, 60, 60, 0.12);
|
||||||
|
--vt-c-divider-dark-1: rgba(84, 84, 84, 0.65);
|
||||||
|
--vt-c-divider-dark-2: rgba(84, 84, 84, 0.48);
|
||||||
|
|
||||||
|
--vt-c-text-light-1: var(--vt-c-indigo);
|
||||||
|
--vt-c-text-light-2: rgba(60, 60, 60, 0.66);
|
||||||
|
--vt-c-text-dark-1: var(--vt-c-white);
|
||||||
|
--vt-c-text-dark-2: rgba(235, 235, 235, 0.64);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* semantic color variables for this project */
|
||||||
|
:root {
|
||||||
|
--color-background: var(--vt-c-white);
|
||||||
|
--color-background-soft: var(--vt-c-white-soft);
|
||||||
|
--color-background-mute: var(--vt-c-white-mute);
|
||||||
|
|
||||||
|
--color-border: var(--vt-c-divider-light-2);
|
||||||
|
--color-border-hover: var(--vt-c-divider-light-1);
|
||||||
|
|
||||||
|
--color-heading: var(--vt-c-text-light-1);
|
||||||
|
--color-text: var(--vt-c-text-light-1);
|
||||||
|
|
||||||
|
--section-gap: 160px;
|
||||||
|
}
|
||||||
|
|
||||||
|
@media (prefers-color-scheme: dark) {
|
||||||
|
:root {
|
||||||
|
--color-background: var(--vt-c-black);
|
||||||
|
--color-background-soft: var(--vt-c-black-soft);
|
||||||
|
--color-background-mute: var(--vt-c-black-mute);
|
||||||
|
|
||||||
|
--color-border: var(--vt-c-divider-dark-2);
|
||||||
|
--color-border-hover: var(--vt-c-divider-dark-1);
|
||||||
|
|
||||||
|
--color-heading: var(--vt-c-text-dark-1);
|
||||||
|
--color-text: var(--vt-c-text-dark-2);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
*,
|
||||||
|
*::before,
|
||||||
|
*::after {
|
||||||
|
box-sizing: border-box;
|
||||||
|
margin: 0;
|
||||||
|
font-weight: normal;
|
||||||
|
}
|
||||||
|
|
||||||
|
body {
|
||||||
|
min-height: 100vh;
|
||||||
|
color: var(--color-text);
|
||||||
|
background: var(--color-background);
|
||||||
|
transition:
|
||||||
|
color 0.5s,
|
||||||
|
background-color 0.5s;
|
||||||
|
line-height: 1.6;
|
||||||
|
font-family:
|
||||||
|
Inter,
|
||||||
|
-apple-system,
|
||||||
|
BlinkMacSystemFont,
|
||||||
|
'Segoe UI',
|
||||||
|
Roboto,
|
||||||
|
Oxygen,
|
||||||
|
Ubuntu,
|
||||||
|
Cantarell,
|
||||||
|
'Fira Sans',
|
||||||
|
'Droid Sans',
|
||||||
|
'Helvetica Neue',
|
||||||
|
sans-serif;
|
||||||
|
font-size: 15px;
|
||||||
|
text-rendering: optimizeLegibility;
|
||||||
|
-webkit-font-smoothing: antialiased;
|
||||||
|
-moz-osx-font-smoothing: grayscale;
|
||||||
|
}
|
1
src/assets/images/images/alignment.svg
Normal file
|
@ -0,0 +1 @@
|
||||||
|
<svg width="16" height="16" viewBox="0 0 16 16" xmlns="http://www.w3.org/2000/svg"><path d="M2 13h12v1H2v-1zm0-3h12v1H2v-1zm0-3h12v1H2V7zm0-6h12v1H2V1zm0 3h12v1H2V4z" fill="#3D4757" fill-rule="evenodd"/></svg>
|
After Width: | Height: | Size: 209 B |
1
src/assets/images/images/arrow-left.svg
Normal file
|
@ -0,0 +1 @@
|
||||||
|
<svg width="4" height="7" xmlns="http://www.w3.org/2000/svg"><path fill="#6F6F6F" d="M0 3.5L4 0v7z" fill-rule="evenodd"/></svg>
|
After Width: | Height: | Size: 127 B |
1
src/assets/images/images/arrow-right.svg
Normal file
|
@ -0,0 +1 @@
|
||||||
|
<svg width="4" height="7" xmlns="http://www.w3.org/2000/svg"><path fill="#6F6F6F" d="M4 3.5L0 0v7z" fill-rule="evenodd"/></svg>
|
After Width: | Height: | Size: 127 B |
1
src/assets/images/images/block.svg
Normal file
|
@ -0,0 +1 @@
|
||||||
|
<svg width="16" height="16" xmlns="http://www.w3.org/2000/svg"><g fill="#3D4757"><path d="M8.923 11v1h-2A2 2 0 015 10.55c.328-.15.638-.335.923-.55a1 1 0 001 1h2zm0-6h-2a1 1 0 00-1 1A4.997 4.997 0 005 5.45 2 2 0 016.923 4h2v1z"/><path d="M4 10a2 2 0 100-4 2 2 0 000 4zm0 1a3 3 0 110-6 3 3 0 010 6zm6-9a1 1 0 00-1 1v3a1 1 0 001 1h3a1 1 0 001-1V3a1 1 0 00-1-1h-3zm0-1h3a2 2 0 012 2v3a2 2 0 01-2 2h-3a2 2 0 01-2-2V3a2 2 0 012-2zm0 10a1 1 0 00-1 1v1a1 1 0 001 1h3a1 1 0 001-1v-1a1 1 0 00-1-1h-3zm0-1h3a2 2 0 012 2v1a2 2 0 01-2 2h-3a2 2 0 01-2-2v-1a2 2 0 012-2z"/></g></svg>
|
After Width: | Height: | Size: 568 B |
1
src/assets/images/images/bold.svg
Normal file
|
@ -0,0 +1 @@
|
||||||
|
<svg width="16" height="16" viewBox="0 0 16 16" xmlns="http://www.w3.org/2000/svg"><path d="M8.131 6.9c2.035 0 2.569-.9 2.569-1.869 0-.968-.64-1.831-2.623-1.831H5.2v3.7h2.931zm.524 5.9c2.045 0 2.545-1.305 2.545-2.3 0-.985-.506-2.4-2.81-2.4H5.2v4.7h3.455zM4 2h4.71c2.367 0 3.19 1.583 3.19 3s-.325 1.852-1.1 2.5c1.2.5 1.569 1.379 1.6 3 .03 1.606-.586 3.5-3.769 3.5H4V2z" fill="#3D4757" fill-rule="evenodd"/></svg>
|
After Width: | Height: | Size: 411 B |
1
src/assets/images/images/catalog.svg
Normal file
|
@ -0,0 +1 @@
|
||||||
|
<svg width="16" height="16" viewBox="0 0 16 16" xmlns="http://www.w3.org/2000/svg"><g fill="#3D4757"><path d="M13 0c.552 0 1 .48 1 1.071V13.93c0 .59-.448 1.07-1 1.07H3c-.552 0-1-.48-1-1.071V1.07C2 .48 2.448 0 3 0h10zm0 1H3v13h10V1z"/><path d="M5 10v1H4v-1h1zm6 0v1H6v-1h5zM5 7v1H4V7h1zm6 0v1H6V7h5zM5 4v1H4V4h1zm6 0v1H6V4h5z"/></g></svg>
|
After Width: | Height: | Size: 337 B |
1
src/assets/images/images/center.svg
Normal file
|
@ -0,0 +1 @@
|
||||||
|
<svg width="16" height="16" viewBox="0 0 16 16" xmlns="http://www.w3.org/2000/svg"><path d="M2 13h12v1H2v-1zm2-3h8v1H4v-1zM2 7h12v1H2V7zm0-6h12v1H2V1zm2 3h8v1H4V4z" fill="#3D4757" fill-rule="evenodd"/></svg>
|
After Width: | Height: | Size: 207 B |
1
src/assets/images/images/checkbox.svg
Normal file
|
@ -0,0 +1 @@
|
||||||
|
<svg version="1.1" id="图层_1" xmlns="http://www.w3.org/2000/svg" x="0" y="0" viewBox="0 0 16 16" xml:space="preserve"><style>.st0{fill:#3d4757}</style><g id="_x30_1-文字_x2F_01开始_x2F_任务列表-16px"><path id="合并形状" class="st0" d="M10.1 2H2v11h11V8.7l1-1V13c0 .6-.4 1-1 1H2c-.6 0-1-.4-1-1V2c0-.6.4-1 1-1h9.1l-1 1z"/><path id="路径" class="st0" d="M7.7 8.5l5.7-5.8.9.8-6.1 5.9-.5.5-3.9-3.4.8-.7z"/></g></svg>
|
After Width: | Height: | Size: 428 B |
1
src/assets/images/images/close.svg
Normal file
|
@ -0,0 +1 @@
|
||||||
|
<svg width="16" height="16" viewBox="0 0 16 16" xmlns="http://www.w3.org/2000/svg"><path d="M8.9 8.192l4.242 4.243-.707.707L8.192 8.9 3.95 13.142l-.707-.707 4.242-4.243L3.243 3.95l.707-.707 4.242 4.242 4.243-4.242.707.707L8.9 8.192z" fill="#6A6A6A" fill-rule="evenodd"/></svg>
|
After Width: | Height: | Size: 276 B |
1
src/assets/images/images/codeblock.svg
Normal file
|
@ -0,0 +1 @@
|
||||||
|
<svg width="14" height="14" xmlns="http://www.w3.org/2000/svg"><g fill="none" fill-rule="evenodd"><path stroke="#525C6F" stroke-linejoin="round" d="M4 4.5L1.5 7 4 9.5M10 4.5L12.5 7 10 9.5"></path><rect fill="#525C6F" transform="scale(1 -1) rotate(70 16.711 0)" x="2.671" y="6.53" width="8" height="1" rx=".2"></rect></g></svg>
|
After Width: | Height: | Size: 326 B |
1
src/assets/images/images/color.svg
Normal file
|
@ -0,0 +1 @@
|
||||||
|
<svg width="16" height="16" viewBox="0 0 16 16" xmlns="http://www.w3.org/2000/svg"><path d="M7.997 3.429L6.398 8h3.2L7.997 3.429zM8.497 2L12 12h-1L9.949 9h-3.9L5 12H4L7.496 2h1z" fill="#3D4757" fill-rule="evenodd"/></svg>
|
After Width: | Height: | Size: 221 B |
1
src/assets/images/images/control.svg
Normal file
|
@ -0,0 +1 @@
|
||||||
|
<svg width="16" height="16" xmlns="http://www.w3.org/2000/svg"><g fill="none" fill-rule="evenodd"><path d="M9.793 1.5H3a.5.5 0 00-.5.5v12a.5.5 0 00.5.5h9a.5.5 0 00.5-.5V4.207L9.793 1.5z" stroke="#3D4757"/><g fill="#3D4757"><path d="M7 7h1v5H7z"/><path d="M5 7h5v1H5z"/></g><path fill="#3D4757" fill-rule="nonzero" d="M9 2h1v3H9z"/><path fill="#3D4757" fill-rule="nonzero" d="M9 4h3v1H9z"/></g></svg>
|
After Width: | Height: | Size: 399 B |
1
src/assets/images/images/date.svg
Normal file
|
@ -0,0 +1 @@
|
||||||
|
<svg width="16" height="16" xmlns="http://www.w3.org/2000/svg"><g fill="#3D4757" fill-rule="evenodd"><path d="M7.5 14.154a5.654 5.654 0 100-11.308 5.654 5.654 0 000 11.308zm0 .846a6.5 6.5 0 110-13 6.5 6.5 0 010 13z" fill-rule="nonzero"/><path d="M8 8h4v1H7V4h1v4z"/></g></svg>
|
After Width: | Height: | Size: 276 B |
1
src/assets/images/images/exit-fullscreen.svg
Normal file
|
@ -0,0 +1 @@
|
||||||
|
<svg width="16" height="16" xmlns="http://www.w3.org/2000/svg"><g fill="#3D4757" fill-rule="evenodd"><path d="M9 9h1v4H9z"/><path d="M9 9h4v1H9zM7 7H6V3h1z"/><path d="M7 7H3V6h4z"/></g></svg>
|
After Width: | Height: | Size: 191 B |
1
src/assets/images/images/format.svg
Normal file
|
@ -0,0 +1 @@
|
||||||
|
<svg width="16" height="16" viewBox="0 0 16 16" xmlns="http://www.w3.org/2000/svg"><g fill="#3D4757" fill-rule="evenodd"><path d="M8.213 13H6.8l6.636-6.636-4.243-4.243-7.07 7.071L5.928 13H4.515L1.06 9.546a.5.5 0 010-.707L8.839 1.06a.5.5 0 01.707 0l4.95 4.95a.5.5 0 010 .707L8.213 13z" fill-rule="nonzero"/><path d="M4.536 6.364l4.95 4.95-.707.707-4.95-4.95zM4.521 13h10.03v1H5.496z"/></g></svg>
|
After Width: | Height: | Size: 394 B |
1
src/assets/images/images/highlight.svg
Normal file
|
@ -0,0 +1 @@
|
||||||
|
<svg width="16" height="16" viewBox="0 0 16 16" xmlns="http://www.w3.org/2000/svg"><g fill="#3D4757" fill-rule="evenodd"><path d="M13.31 5h-1.92a2.203 2.203 0 00-.39-.034c-.135 0-.27.012-.402.034H10v.18c-.578.256-1 .714-1 1.214v1.928c0 .196.117.43.3.658v1.23a3.543 3.543 0 01-.3-.4V11H8V1h1v4.265C9 4.763 10 4 10.942 4c1.19 0 1.92.422 2.367 1zM2 6c-.03-.498-.175-2 2.5-2C7.11 4 7 5 7 6.902V11H5.984v-.993c.38.662-.115.993-1.484.993C2.708 11 2 9.931 2 9c0-1.428.447-2 2.5-2h1.484c0-1 .031-2-1.484-2-1.533 0-1.577.485-1.577 1H2zm2.5 2C3.601 8 3 7.768 3 9c0 1.31.438 1 1.5 1 .617 0 1.484-.665 1.484-1.847V8H4.5z"/><path d="M13.085 6.316l-2.814 3a1 1 0 101.458 1.368l2.815-3a1 1 0 00-1.459-1.368z" fill-rule="nonzero"/></g></svg>
|
After Width: | Height: | Size: 725 B |
1
src/assets/images/images/hyperlink.svg
Normal file
|
@ -0,0 +1 @@
|
||||||
|
<svg width="16" height="16" xmlns="http://www.w3.org/2000/svg"><g transform="rotate(45 5.5 13.328)" fill="#3D4757" fill-rule="evenodd"><path d="M7 6H6V3.515a2.5 2.5 0 10-5 0V6H0V3.515a3.5 3.5 0 117 0V6zm0 4v2.5a3.5 3.5 0 01-7 0V10h1v2.5a2.5 2.5 0 105 0V10h1z" fill-rule="nonzero"/><rect x="3.062" y="5.209" width="1" height="5.5" rx=".5"/></g></svg>
|
After Width: | Height: | Size: 349 B |
1
src/assets/images/images/image.svg
Normal file
|
@ -0,0 +1 @@
|
||||||
|
<svg version="1.1" id="图层_1" xmlns="http://www.w3.org/2000/svg" x="0" y="0" viewBox="0 0 16 16" xml:space="preserve"><style>.st0{fill:#3d4757}</style><g id="_x30_0-公共_x2F_02工具栏_x2F_插入图片-16px-"><g id="Group-19" transform="translate(1 1)"><path id="Combined-Shape" class="st0" d="M1 0h12c.6 0 1 .4 1 1v11c0 .6-.4 1-1 1H1c-.6 0-1-.4-1-1V1c0-.6.4-1 1-1zm0 1v11h12V1H1z"/><circle id="椭圆形" class="st0" cx="10" cy="4" r="1"/><path id="Path" class="st0" d="M8.5 11.2l-4-4.1L1 10.7V9.2c1.7-1.6 2.7-2.5 3-2.8.4-.5.7-.4 1 0L8.5 10 11 7.3c.4-.5.6-.5 1-.1l2 2.8v1.5l-2.5-3.4-3 3.1z"/></g></g></svg>
|
After Width: | Height: | Size: 613 B |
1
src/assets/images/images/italic.svg
Normal file
|
@ -0,0 +1 @@
|
||||||
|
<svg width="16" height="16" viewBox="0 0 16 16" xmlns="http://www.w3.org/2000/svg"><path d="M10.017 3L8.08 13H9v1H6v-1h1.182L9 3H8V2h3v1h-.983z" fill="#3D4757"/></svg>
|
After Width: | Height: | Size: 167 B |
1
src/assets/images/images/latex.svg
Normal file
|
@ -0,0 +1 @@
|
||||||
|
<svg width="16" height="16" xmlns="http://www.w3.org/2000/svg"><g fill="none" fill-rule="evenodd"><path d="M9 13.5H2.982a.5.5 0 01-.404-.794l3.208-4.412a.5.5 0 000-.588L2.578 3.294a.5.5 0 01.404-.794H9" stroke="#3D4757"/><path d="M14.447 7l.809.588-2.139 2.942 2.139 2.942-.81.588-1.946-2.68-1.947 2.68-.809-.588 2.138-2.942-2.138-2.942.81-.588L12.5 9.679 14.447 7z" fill="#3D4757"/></g></svg>
|
After Width: | Height: | Size: 393 B |
1
src/assets/images/images/left.svg
Normal file
|
@ -0,0 +1 @@
|
||||||
|
<svg height="16" viewBox="0 0 16 16" width="16" xmlns="http://www.w3.org/2000/svg"><path d="M2 13h12v1H2zm0-3h8v1H2zm0-3h12v1H2zm0-6h12v1H2zm0 3h8v1H2z" fill="#3d4757" fill-rule="evenodd"/></svg>
|
After Width: | Height: | Size: 195 B |
1
src/assets/images/images/line-dash-dot-dot.svg
Normal file
|
@ -0,0 +1 @@
|
||||||
|
<svg width="126" height="20" xmlns="http://www.w3.org/2000/svg"><path d="M4 10h5v1H4zm7 0h2v1h-2zm4 0h2v1h-2zm4 0h5v1h-5zm7 0h2v1h-2zm4 0h2v1h-2zm4 0h5v1h-5zm7 0h2v1h-2zm4 0h2v1h-2zm4 0h5v1h-5zm7 0h2v1h-2zm4 0h2v1h-2zm4 0h5v1h-5zm7 0h2v1h-2zm4 0h2v1h-2zm4 0h5v1h-5zm7 0h2v1h-2zm4 0h2v1h-2zm4 0h5v1h-5zm7 0h2v1h-2zm4 0h2v1h-2zm4 0h5v1h-5zm7 0h2v1h-2zm4 0h2v1h-2z" fill-rule="evenodd"/></svg>
|
After Width: | Height: | Size: 390 B |
1
src/assets/images/images/line-dash-dot.svg
Normal file
|
@ -0,0 +1 @@
|
||||||
|
<svg width="126" height="20" xmlns="http://www.w3.org/2000/svg"><path d="M4 10h6v1H4zm9 0h3v1h-3zm6 0h6v1h-6zm9 0h3v1h-3zm6 0h6v1h-6zm9 0h3v1h-3zm6 0h6v1h-6zm9 0h3v1h-3zm6 0h6v1h-6zm9 0h3v1h-3zm6 0h6v1h-6zm9 0h3v1h-3zm6 0h6v1h-6zm9 0h3v1h-3zm6 0h6v1h-6zm9 0h3v1h-3z" fill-rule="evenodd"/></svg>
|
After Width: | Height: | Size: 294 B |
1
src/assets/images/images/line-dash-large-gap.svg
Normal file
|
@ -0,0 +1 @@
|
||||||
|
<svg width="126" height="20" xmlns="http://www.w3.org/2000/svg"><path d="M5 10h4v1H5zm8 0h4v1h-4zm8 0h4v1h-4zm8 0h4v1h-4zm8 0h4v1h-4zm8 0h4v1h-4zm8 0h4v1h-4zm8 0h4v1h-4zm8 0h4v1h-4zm8 0h4v1h-4zm8 0h4v1h-4zm8 0h4v1h-4zm8 0h4v1h-4zm8 0h4v1h-4zm8 0h4v1h-4z" fill-rule="evenodd"/></svg>
|
After Width: | Height: | Size: 282 B |
1
src/assets/images/images/line-dash-small-gap.svg
Normal file
|
@ -0,0 +1 @@
|
||||||
|
<svg width="126" height="20" xmlns="http://www.w3.org/2000/svg"><path d="M4 10h4v1H4zm5 0h4v1H9zm5 0h4v1h-4zm5 0h4v1h-4zm5 0h4v1h-4zm5 0h4v1h-4zm5 0h4v1h-4zm5 0h4v1h-4zm5 0h4v1h-4zm5 0h4v1h-4zm5 0h4v1h-4zm5 0h4v1h-4zm5 0h4v1h-4zm5 0h4v1h-4zm5 0h4v1h-4zm5 0h4v1h-4zm5 0h4v1h-4zm5 0h4v1h-4zm5 0h4v1h-4zm5 0h4v1h-4zm5 0h4v1h-4zm5 0h4v1h-4zm5 0h4v1h-4zm5 0h3v1h-3z" fill-rule="evenodd"/></svg>
|
After Width: | Height: | Size: 389 B |
1
src/assets/images/images/line-dot.svg
Normal file
|
@ -0,0 +1 @@
|
||||||
|
<svg width="126" height="20" xmlns="http://www.w3.org/2000/svg"><path d="M4 10h1v1H4zm12 0h1v1h-1zM6 10h1v1H6zm12 0h1v1h-1zM8 10h1v1H8zm12 0h1v1h-1zm-10 0h1v1h-1zm12 0h1v1h-1zm-10 0h1v1h-1zm12 0h1v1h-1zm-10 0h1v1h-1zm12 0h1v1h-1zm2 0h1v1h-1zm12 0h1v1h-1zm-10 0h1v1h-1zm12 0h1v1h-1zm-10 0h1v1h-1zm12 0h1v1h-1zm-10 0h1v1h-1zm12 0h1v1h-1zm-10 0h1v1h-1zm12 0h1v1h-1zm-10 0h1v1h-1zm12 0h1v1h-1zm2 0h1v1h-1zm12 0h1v1h-1zm-10 0h1v1h-1zm12 0h1v1h-1zm-10 0h1v1h-1zm12 0h1v1h-1zm-10 0h1v1h-1zm12 0h1v1h-1zm-10 0h1v1h-1zm12 0h1v1h-1zm-10 0h1v1h-1zm12 0h1v1h-1zm2 0h1v1h-1zm12 0h1v1h-1zm-10 0h1v1h-1zm12 0h1v1h-1zm-10 0h1v1h-1zm12 0h1v1h-1zm-10 0h1v1h-1zm12 0h1v1h-1zm-10 0h1v1h-1zm12 0h1v1h-1zm-10 0h1v1h-1zm12 0h1v1h-1zm2 0h1v1h-1zm12 0h1v1h-1zm-10 0h1v1h-1zm12 0h1v1h-1zm-10 0h1v1h-1zm12 0h1v1h-1zm-10 0h1v1h-1zm12 0h1v1h-1zm-10 0h1v1h-1zm12 0h1v1h-1zm-10 0h1v1h-1z" fill-rule="evenodd"/></svg>
|
After Width: | Height: | Size: 885 B |
1
src/assets/images/images/line-single.svg
Normal file
|
@ -0,0 +1 @@
|
||||||
|
<svg width="126" height="20" xmlns="http://www.w3.org/2000/svg"><path d="M4 10h118v1H4z" fill-rule="evenodd"/></svg>
|
After Width: | Height: | Size: 116 B |
1
src/assets/images/images/list.svg
Normal file
|
@ -0,0 +1 @@
|
||||||
|
<svg width="16" height="16" viewBox="0 0 16 16" xmlns="http://www.w3.org/2000/svg"><g fill="none" fill-rule="evenodd"><path fill="#3D4757" d="M7 12h7v1H7zm0-5h7v1H7zm0-5h7v1H7zM3 4V2H2V1h2v3h1v1H2V4h1z"/><path d="M2 6h3v1H2V6zm0 3h3v1H2V9z" fill="#4F4F4F"/><path fill="#3D4757" fill-rule="nonzero" d="M4.5 6L5 7l-2.5 3L2 9z"/><path d="M4 14l-1-2H2v-1h3v1H4l1 2v1H2v-1h2z" fill="#3D4757"/></g></svg>
|
After Width: | Height: | Size: 398 B |
1
src/assets/images/images/page-break.svg
Normal file
|
@ -0,0 +1 @@
|
||||||
|
<svg version="1.1" id="图层_1" xmlns="http://www.w3.org/2000/svg" x="0" y="0" viewBox="0 0 16 16" xml:space="preserve"><style>.st0{fill:none;stroke:#3d4757}.st1{fill:#3d4757}</style><g id="_x30_1-文字_x2F_02插入_x2F_分页-16px"><path id="矩形" class="st0" d="M5.5 2.5h7c.6 0 1 .4 1 1v3c0 .6-.4 1-1 1h-7c-.6 0-1-.4-1-1v-3c0-.6.4-1 1-1z"/><path id="三角形" class="st1" d="M4 8.5L1 6v5z"/><path id="合并形状" class="st0" d="M10.8 9.5H5c-.3 0-.5.2-.5.5v4c0 .3.2.5.5.5h8c.3 0 .5-.2.5-.5v-1.8l-2.7-2.7z"/><path id="矩形_1_" class="st1" d="M10 10h1v3h-1z"/><path id="矩形-copy-2" class="st1" d="M10 12h3v1h-3z"/></g></svg>
|
After Width: | Height: | Size: 635 B |
1
src/assets/images/images/page-mode.svg
Normal file
|
@ -0,0 +1 @@
|
||||||
|
<svg width="16" height="16" viewBox="0 0 16 16" xmlns="http://www.w3.org/2000/svg"><g fill="none" fill-rule="evenodd"><g transform="translate(2 1)"><rect stroke="#3D4757" x=".5" y=".5" width="11" height="8" rx="1"/><path fill="#3D4757" fill-rule="nonzero" d="M2 3h4v1H2zm0 2h8v1H2z"/></g><g fill="#3D4757" fill-rule="nonzero"><path d="M14 15h-1v-5H3v5H2V9h12v6z"/><path d="M4 12h4v1H4zm0 2h8v1H4z"/></g></g></svg>
|
After Width: | Height: | Size: 413 B |
1
src/assets/images/images/page-scale-add.svg
Normal file
|
@ -0,0 +1 @@
|
||||||
|
<svg width="16" height="16" viewBox="0 0 16 16" xmlns="http://www.w3.org/2000/svg"><path d="M7 7V3h2v4h4v2H9v4H7V9H3V7h4z" fill="#636363" fill-rule="evenodd"/></svg>
|
After Width: | Height: | Size: 165 B |
1
src/assets/images/images/page-scale-minus.svg
Normal file
|
@ -0,0 +1 @@
|
||||||
|
<svg width="16" height="16" viewBox="0 0 16 16" xmlns="http://www.w3.org/2000/svg"><path d="M3 7h10v2H3z" fill="#636363" fill-rule="evenodd"/></svg>
|
After Width: | Height: | Size: 148 B |
1
src/assets/images/images/painter.svg
Normal file
|
@ -0,0 +1 @@
|
||||||
|
<svg width="16" height="16" viewBox="0 0 16 16" xmlns="http://www.w3.org/2000/svg"><g fill="none" fill-rule="evenodd"><path d="M7.5 2v2.5H4a.5.5 0 00-.5.5v2a.5.5 0 00.5.5h9a.5.5 0 00.5-.5V5a.5.5 0 00-.5-.5H9.5V2a.5.5 0 00-.5-.5H8a.5.5 0 00-.5.5z" stroke="#3D4757"/><path fill="#3D4757" d="M13 7h1v4h-1z"/><path d="M11 13a2 2 0 002-2V8.764A3 3 0 118.764 13H11z" fill="#3D4757"/><path fill="#3D4757" d="M1 13h10v1H1z"/><path d="M1 13a2 2 0 002-2V8.764A3 3 0 011 14v-1z" fill="#3D4757"/><path fill="#3D4757" d="M3 7h1v4H3z"/></g></svg>
|
After Width: | Height: | Size: 532 B |
1
src/assets/images/images/paper-direction.svg
Normal file
|
@ -0,0 +1 @@
|
||||||
|
<svg version="1.1" id="图层_1" xmlns="http://www.w3.org/2000/svg" x="0" y="0" viewBox="0 0 16 16" xml:space="preserve"><style>.st0{fill:#3d4757}</style><g id="_x30_1-文字_x2F_04页面_x2F_纸张方向-16px"><g id="编组" transform="translate(1 1)"><path id="合并形状" class="st0" d="M14 6v7c0 .6-.4 1-1 1H4c-.6 0-1-.4-1-1V6c0-.6.4-1 1-1h9c.6 0 1 .4 1 1zm-1 0H4v7h9V6z"/><path id="路径" class="st0" d="M9 4H8V1H1v9h1v1H1c-.6 0-1-.4-1-1V1c0-.6.4-1 1-1h7c.6 0 1 .4 1 1v3z"/><path id="矩形" class="st0" d="M11 7h1v5h-1z"/><path id="矩形-copy-2" class="st0" d="M2 2h5v1H2z"/></g></g></svg>
|
After Width: | Height: | Size: 599 B |
1
src/assets/images/images/paper-margin.svg
Normal file
|
@ -0,0 +1 @@
|
||||||
|
<svg width="16" height="16" xmlns="http://www.w3.org/2000/svg"><g fill="none" fill-rule="evenodd"><rect stroke="#3D4757" x="2.5" y="1.5" width="11" height="13" rx="1"/><path fill="#3D4757" fill-rule="nonzero" d="M3 4h10v1H3zm0 7h10v1H3z"/><path fill="#3D4757" fill-rule="nonzero" d="M5 14V2h1v12zm5 0V2h1v12z"/></g></svg>
|
After Width: | Height: | Size: 321 B |
1
src/assets/images/images/paper-size.svg
Normal file
|
@ -0,0 +1 @@
|
||||||
|
<svg width="16" height="16" xmlns="http://www.w3.org/2000/svg"><g fill="none" fill-rule="evenodd"><g fill-rule="nonzero"><path d="M10.793 1.5L13.5 4.207V14L3 14.5 2.5 2l8.293-.5z" stroke="#3D4757"/><path fill="#3D4757" d="M10 2h1v3h-1z"/><path fill="#3D4757" d="M10 4h3v1h-3z"/></g><path d="M7 3v1H5v2H4V3h3z" fill="#3D4757"/><path fill="#3D4757" d="M5.169 3.43l6.62 8.784-.799.602-6.62-8.785z"/><path d="M9 13v-1h2v-2h1v3H9z" fill="#3D4757"/></g></svg>
|
After Width: | Height: | Size: 453 B |
1
src/assets/images/images/print.svg
Normal file
|
@ -0,0 +1 @@
|
||||||
|
<svg width="16" height="16" viewBox="0 0 16 16" xmlns="http://www.w3.org/2000/svg"><g fill="#3D4757" fill-rule="evenodd"><path d="M12 4h-1V2H5v2H4V2a1 1 0 011-1h6a1 1 0 011 1v2zm0 5v4a1 1 0 01-1 1H5a1 1 0 01-1-1V9h1v4h6V9h1z"/><path d="M12 12v-1h2V5H2v6h2v1H2a1 1 0 01-1-1V5a1 1 0 011-1h12a1 1 0 011 1v6a1 1 0 01-1 1h-2z"/><path d="M3 8h10v1H3zm8-2h2v1h-2z"/></g></svg>
|
After Width: | Height: | Size: 369 B |
1
src/assets/images/images/redo.svg
Normal file
|
@ -0,0 +1 @@
|
||||||
|
<svg width="16" height="16" viewBox="0 0 16 16" xmlns="http://www.w3.org/2000/svg"><path d="M3 14v-3a4 4 0 014-4h3V6H7a5 5 0 00-5 5v3h1zm7.016-11.282v7.543l4.29-3.73z" fill="#3D4757"/></svg>
|
After Width: | Height: | Size: 190 B |
1
src/assets/images/images/request-fullscreen.svg
Normal file
|
@ -0,0 +1 @@
|
||||||
|
<svg width="16" height="16" viewBox="0 0 16 16" xmlns="http://www.w3.org/2000/svg"><g fill="#3D4757" fill-rule="evenodd"><path d="M3 3h1v4H3z"/><path d="M3 3h4v1H3zm10 10h-1V9h1z"/><path d="M13 13H9v-1h4z"/></g></svg>
|
After Width: | Height: | Size: 217 B |
1
src/assets/images/images/right.svg
Normal file
|
@ -0,0 +1 @@
|
||||||
|
<svg width="16" height="16" viewBox="0 0 16 16" xmlns="http://www.w3.org/2000/svg"><path d="M2 13h12v1H2v-1zm4-3h8v1H6v-1zM2 7h12v1H2V7zm0-6h12v1H2V1zm4 3h8v1H6V4z" fill="#3D4757" fill-rule="evenodd"/></svg>
|
After Width: | Height: | Size: 207 B |
1
src/assets/images/images/row-margin.svg
Normal file
|
@ -0,0 +1 @@
|
||||||
|
<svg width="16" height="16" viewBox="0 0 16 16" xmlns="http://www.w3.org/2000/svg"><path d="M2 14h12v1H2v-1zm7-5h5v1H9V9zm0-3h5v1H9V6zM2 1h12v1H2V1zm2.5 3L7 7H2zm0 8L7 9H2z" fill="#3D4757" fill-rule="evenodd"/></svg>
|
After Width: | Height: | Size: 216 B |
1
src/assets/images/images/search.svg
Normal file
|
@ -0,0 +1 @@
|
||||||
|
<svg width="16" height="16" viewBox="0 0 16 16" xmlns="http://www.w3.org/2000/svg"><g fill="none" fill-rule="evenodd"><circle stroke="#3D4757" cx="6" cy="6" r="4.5"/><path d="M10.061 10.968L8.707 9.414l.707-.707 1.514 1.457.435-.404 2.632 2.462a1.154 1.154 0 01.05 1.635 1.184 1.184 0 01-1.655.064l-2.788-2.527.46-.426z" fill="#3D4757" fill-rule="nonzero"/></g></svg>
|
After Width: | Height: | Size: 367 B |
1
src/assets/images/images/separator.svg
Normal file
|
@ -0,0 +1 @@
|
||||||
|
<svg width="16" height="16" xmlns="http://www.w3.org/2000/svg"><path d="M3.9 2.8l2.01 2.506c.2.25.58.25.78 0L8.7 2.799l2.01 2.507c.2.25.58.25.78 0l2.4-2.993-.78-.626-2.01 2.507-2.01-2.507a.5.5 0 00-.78 0L6.3 4.194 4.29 1.687a.5.5 0 00-.78 0l-2.4 3 .78.625L3.9 2.8zM1 8h13v1H1zm0 4h3v1H1zm5 0h3v1H6zm5 0h3v1h-3z" fill="#3D4757"/></svg>
|
After Width: | Height: | Size: 334 B |
1
src/assets/images/images/signature-undo.svg
Normal file
|
@ -0,0 +1 @@
|
||||||
|
<svg width="24" height="24" xmlns="http://www.w3.org/2000/svg"><path d="M8 6h5.5a7 7 0 010 14v-2a5 5 0 000-10H8v3L4 7l4-4v3z" fill="#3d4757" fill-rule="evenodd"/></svg>
|
After Width: | Height: | Size: 168 B |
1
src/assets/images/images/signature.svg
Normal file
|
@ -0,0 +1 @@
|
||||||
|
<svg width="16" height="16" xmlns="http://www.w3.org/2000/svg"><g fill="none" fill-rule="evenodd"><path fill="#3D4757" d="M2 13h12v1H2z"/><path fill="#4B5463" fill-rule="nonzero" d="M5.26 8.458l2.23 1.28L6 12H3z"/><path d="M5.666 6.149L4.31 8.168l4.045 2.48 1.503-2.159-4.192-2.34zm1.106-4.156l-1.986 3.44 6.3 3.648 2.037-2.943-6.351-4.145z" stroke="#4B5463"/></g></svg>
|
After Width: | Height: | Size: 370 B |
1
src/assets/images/images/size-add.svg
Normal file
|
@ -0,0 +1 @@
|
||||||
|
<svg width="16" height="16" viewBox="0 0 16 16" xmlns="http://www.w3.org/2000/svg"><g fill="#3D4757" fill-rule="evenodd"><path d="M6.215 3.29H7.64L11.855 14H10.52l-1.14-3H4.46l-1.14 3H2L6.215 3.29zM4.85 9.965h4.14L6.965 4.61h-.06L4.85 9.965z"/><path d="M12 4V2h1v2h2v1h-2v2h-1V5h-2V4h2z" fill-rule="nonzero"/></g></svg>
|
After Width: | Height: | Size: 319 B |
1
src/assets/images/images/size-minus.svg
Normal file
|
@ -0,0 +1 @@
|
||||||
|
<svg width="16" height="16" viewBox="0 0 16 16" xmlns="http://www.w3.org/2000/svg"><g fill="#3D4757" fill-rule="evenodd"><path fill-rule="nonzero" d="M11 4h4v1h-4z"/><path d="M6.215 3.29H7.64L11.855 14H10.52l-1.14-3H4.46l-1.14 3H2L6.215 3.29zM4.85 9.965h4.14L6.965 4.61h-.06L4.85 9.965z"/></g></svg>
|
After Width: | Height: | Size: 299 B |
1
src/assets/images/images/strikeout.svg
Normal file
|
@ -0,0 +1 @@
|
||||||
|
<svg width="16" height="16" viewBox="0 0 16 16" xmlns="http://www.w3.org/2000/svg"><g fill="#3D4757" fill-rule="evenodd"><path d="M10.42 7.903H6.692a9.182 9.182 0 01-.41-.172 5.54 5.54 0 01-.814-.447 2.955 2.955 0 01-.655-.595 2.728 2.728 0 01-.44-.777 2.877 2.877 0 01-.162-1.006c0-.472.094-.888.282-1.25.188-.36.453-.663.793-.907s.747-.43 1.22-.558A5.97 5.97 0 018.063 2c.504 0 .95.049 1.337.147.387.097.725.23 1.013.398.287.169.53.365.73.59a3.337 3.337 0 01.772 1.486c.03.13.054.255.073.379h-1.276a2.393 2.393 0 00-.22-.615 2.315 2.315 0 00-.59-.724 2.467 2.467 0 00-.834-.44 3.376 3.376 0 00-1.005-.146 4.69 4.69 0 00-.958.097 2.77 2.77 0 00-.839.314 1.765 1.765 0 00-.597.566c-.152.233-.229.518-.229.854 0 .348.086.642.258.884.171.241.401.449.689.622.287.174.615.323.983.448s.749.247 1.142.367c.31.097.62.196.934.297a8.439 8.439 0 01.973.38zm1.376 1c.175.217.315.466.418.746.105.285.158.612.158.98 0 .554-.104 1.041-.312 1.462-.207.42-.496.772-.867 1.054-.37.282-.81.495-1.32.64A6.12 6.12 0 018.205 14c-.543 0-1.071-.09-1.586-.273a4.44 4.44 0 01-1.374-.773 3.873 3.873 0 01-.97-1.217 3.695 3.695 0 01-.395-1.612h1.27c.028.407.122.78.282 1.12a2.835 2.835 0 001.581 1.465c.363.138.76.207 1.192.207.387 0 .758-.042 1.112-.126a2.85 2.85 0 00.938-.399 2.01 2.01 0 00.647-.708c.16-.29.241-.642.241-1.054 0-.337-.087-.623-.261-.86a2.333 2.333 0 00-.69-.61 4.651 4.651 0 00-.495-.257h2.099z"/><path d="M3 7h10v1H3z"/></g></svg>
|
After Width: | Height: | Size: 1.4 KiB |
1
src/assets/images/images/subscript.svg
Normal file
|
@ -0,0 +1 @@
|
||||||
|
<svg version="1.1" id="图层_1" xmlns="http://www.w3.org/2000/svg" x="0" y="0" viewBox="0 0 16 16" xml:space="preserve"><style>.st0{fill:#3d4757}</style><g id="_x30_0-公共_x2F_02工具栏_x2F_subscript"><path id="_x32_" class="st0" d="M15 13.3v.7h-3c0-.3.1-.5.3-.8.2-.2.5-.6 1-1 .4-.3.6-.5.7-.7.1-.2.2-.3.2-.5s-.1-.3-.2-.4c-.1-.1-.2-.1-.4-.1s-.3 0-.4.1-.2.4-.2.7l-.9-.1c.1-.4.2-.7.5-.9.3-.2.6-.3 1-.3s.8.1 1 .3c.3.2.4.5.4.8 0 .2 0 .4-.1.5-.1.2-.2.3-.3.5-.1.1-.3.3-.6.5s-.4.4-.5.4c-.1.1-.1.2-.2.3H15z"/><path id="合并形状" class="st0" d="M7.2 8.5l4 5.5H9.8L6.5 9.4 3.2 14H1.8l4-5.5-4-5.5h1.4l3.3 4.6L9.8 3h1.3L7.2 8.5z"/></g></svg>
|
After Width: | Height: | Size: 637 B |
1
src/assets/images/images/superscript.svg
Normal file
|
@ -0,0 +1 @@
|
||||||
|
<svg version="1.1" id="图层_1" xmlns="http://www.w3.org/2000/svg" x="0" y="0" viewBox="0 0 16 16" xml:space="preserve"><style>.st0{fill:#3d4757}</style><g id="_x30_0-公共_x2F_02工具栏_x2F_superscript"><path id="_x32_" class="st0" d="M15 6.3V7h-3c0-.3.1-.5.3-.8.2-.2.5-.6 1-1 .3-.2.6-.5.7-.6.1-.2.2-.3.2-.5s-.1-.3-.2-.4c-.1-.1-.2-.1-.4-.1s-.3 0-.4.1-.2.3-.2.6l-.9-.1c.1-.4.2-.7.5-.9s.6-.3 1-.3.8.1 1 .3c.3.2.4.5.4.8 0 .2 0 .4-.1.5s-.2.4-.4.5c-.1.1-.3.3-.6.5s-.4.4-.4.5c-.1.1-.1.2-.2.3l1.7-.1z"/><path id="合并形状" class="st0" d="M7.4 8.5l4 5.5H10L6.7 9.4 3.4 14H2l4-5.5L2 3h1.4l3.3 4.6L10 3h1.3L7.4 8.5z"/></g></svg>
|
After Width: | Height: | Size: 627 B |
1
src/assets/images/images/table.svg
Normal file
|
@ -0,0 +1 @@
|
||||||
|
<svg width="16" height="16" xmlns="http://www.w3.org/2000/svg"><g fill="none" fill-rule="evenodd"><rect x=".5" y=".5" width="12" height="12" rx="1" transform="translate(1 1)" stroke="#3D4757"/><path fill="#3D4757" fill-rule="nonzero" d="M2 9h12v1H2zm0-4h12v1H2z"/><path fill="#3D4757" fill-rule="nonzero" d="M5 1h1v13H5zm4 0h1v13H9z"/></g></svg>
|
After Width: | Height: | Size: 345 B |
1
src/assets/images/images/title.svg
Normal file
|
@ -0,0 +1 @@
|
||||||
|
<svg width="16" height="16" xmlns="http://www.w3.org/2000/svg"><g fill="#3D4757" fill-rule="evenodd"><path d="M14 1a1 1 0 011 1v12a1 1 0 01-1 1H2a1 1 0 01-1-1V2a1 1 0 011-1h12zm0 1H2v12h12V2z" fill-rule="nonzero"/><path fill-rule="nonzero" d="M4 11h8v1H4zm0-3h4v1H4zm0-3h2v1H4z"/><path d="M9 5h1v4H9z"/><path d="M7 5h5v1H7z"/></g></svg>
|
After Width: | Height: | Size: 336 B |
1
src/assets/images/images/trash.svg
Normal file
|
@ -0,0 +1 @@
|
||||||
|
<svg width="24" height="24" xmlns="http://www.w3.org/2000/svg"><g fill="#3d4757" fill-rule="evenodd"><path d="M17 3v4h4v2h-2v13H6V9H4V7h4V3h9zm0 6H8v11h9V9zm-2-4h-5v2h5V5z" fill-rule="nonzero"/><path d="M10 10h2v7h-2zm3 0h2v7h-2z"/></g></svg>
|
After Width: | Height: | Size: 242 B |
1
src/assets/images/images/underline.svg
Normal file
|
@ -0,0 +1 @@
|
||||||
|
<svg width="16" height="16" viewBox="0 0 16 16" xmlns="http://www.w3.org/2000/svg"><path d="M5 2v6a3 3 0 106 0V2h1v6a4 4 0 11-8 0V2h1zM4 13h8v1H4z" fill="#3D4757"/></svg>
|
After Width: | Height: | Size: 170 B |
1
src/assets/images/images/undo.svg
Normal file
|
@ -0,0 +1 @@
|
||||||
|
<svg width="16" height="16" viewBox="0 0 16 16" xmlns="http://www.w3.org/2000/svg"><path d="M6 2.763v7.544l-4.29-3.73zM13 14v-3a4 4 0 00-4-4H6V6h3a5 5 0 015 5v3h-1z" fill="#3D4757"/></svg>
|
After Width: | Height: | Size: 188 B |
1
src/assets/images/images/watermark.svg
Normal file
|
@ -0,0 +1 @@
|
||||||
|
<svg width="16" height="16" xmlns="http://www.w3.org/2000/svg"><g fill="none" fill-rule="evenodd"><rect stroke="#3D4757" x="2.5" y="1.5" width="11" height="13" rx="1"/><path d="M4 7h8v1H4V7zm0-2h8v1H4V5zm0 6h8v1H4v-1zm0-2h8v1H4V9z" fill="#909AA9" fill-rule="nonzero"/><path d="M6 5.623c.36-.354.936-.638 2-.604 1.785.057 2-.008 2 1.894v4.098H8.984v-.993c1.046.662.885.993-.484.993-1.792 0-2.5-1.068-2.5-2 0-1.427.447-2 2.5-2h.484c0-1-.006-1.007-.984-1-.978.008-1.419.437-2 .437v-.825zm2.5 2.389c-.899 0-1.5-.232-1.5 1 0 1.31.438 1 1.5 1 .617 0 .484-.665.484-1.848v-.152H8.5z" fill="#3D4757"/></g></svg>
|
After Width: | Height: | Size: 602 B |
1
src/assets/images/images/word-tool.svg
Normal file
|
@ -0,0 +1 @@
|
||||||
|
<svg width="16" height="16" xmlns="http://www.w3.org/2000/svg"><g fill="#3D4757" fill-rule="evenodd"><path d="M1 0h1v15H1zm5 4h7v1H6zm-3 6h7v1H3z"/><path d="M1 0h4v1H1zm10 14h4v1h-4zM3 7h10v1H3z"/><path d="M14 0h1v15h-1zM8 0l3 3V0zm6 0h-3v1h3zM8 15l-3-3v3zm-6-1h3v1H2z"/></g></svg>
|
After Width: | Height: | Size: 281 B |
1
src/assets/logo.svg
Normal file
|
@ -0,0 +1 @@
|
||||||
|
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 261.76 226.69"><path d="M161.096.001l-30.225 52.351L100.647.001H-.005l130.877 226.688L261.749.001z" fill="#41b883"/><path d="M161.096.001l-30.225 52.351L100.647.001H52.346l78.526 136.01L209.398.001z" fill="#34495e"/></svg>
|
After Width: | Height: | Size: 276 B |
35
src/assets/main.css
Normal file
|
@ -0,0 +1,35 @@
|
||||||
|
@import './base.css';
|
||||||
|
|
||||||
|
#app {
|
||||||
|
max-width: 1280px;
|
||||||
|
margin: 0 auto;
|
||||||
|
padding: 2rem;
|
||||||
|
font-weight: normal;
|
||||||
|
}
|
||||||
|
|
||||||
|
a,
|
||||||
|
.green {
|
||||||
|
text-decoration: none;
|
||||||
|
color: hsla(160, 100%, 37%, 1);
|
||||||
|
transition: 0.4s;
|
||||||
|
padding: 3px;
|
||||||
|
}
|
||||||
|
|
||||||
|
@media (hover: hover) {
|
||||||
|
a:hover {
|
||||||
|
background-color: hsla(160, 100%, 37%, 0.2);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@media (min-width: 1024px) {
|
||||||
|
body {
|
||||||
|
display: flex;
|
||||||
|
place-items: center;
|
||||||
|
}
|
||||||
|
|
||||||
|
#app {
|
||||||
|
display: grid;
|
||||||
|
grid-template-columns: 1fr 1fr;
|
||||||
|
padding: 0 2rem;
|
||||||
|
}
|
||||||
|
}
|
1078
src/assets/style.css
Normal file
39
src/components/HelloWorld.vue
Normal file
|
@ -0,0 +1,39 @@
|
||||||
|
<script setup>
|
||||||
|
defineProps({
|
||||||
|
msg: {
|
||||||
|
type: String,
|
||||||
|
required: true
|
||||||
|
}
|
||||||
|
})
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<template>
|
||||||
|
<div class="">
|
||||||
|
|
||||||
|
</div>
|
||||||
|
</template>
|
||||||
|
|
||||||
|
<style scoped>
|
||||||
|
h1 {
|
||||||
|
font-weight: 500;
|
||||||
|
font-size: 2.6rem;
|
||||||
|
position: relative;
|
||||||
|
top: -10px;
|
||||||
|
}
|
||||||
|
|
||||||
|
h3 {
|
||||||
|
font-size: 1.2rem;
|
||||||
|
}
|
||||||
|
|
||||||
|
.greetings h1,
|
||||||
|
.greetings h3 {
|
||||||
|
text-align: center;
|
||||||
|
}
|
||||||
|
|
||||||
|
@media (min-width: 1024px) {
|
||||||
|
.greetings h1,
|
||||||
|
.greetings h3 {
|
||||||
|
text-align: left;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
</style>
|
12
src/components/TheWelcome.vue
Normal file
|
@ -0,0 +1,12 @@
|
||||||
|
<script setup>
|
||||||
|
import WelcomeItem from './WelcomeItem.vue'
|
||||||
|
import DocumentationIcon from './icons/IconDocumentation.vue'
|
||||||
|
import ToolingIcon from './icons/IconTooling.vue'
|
||||||
|
import EcosystemIcon from './icons/IconEcosystem.vue'
|
||||||
|
import CommunityIcon from './icons/IconCommunity.vue'
|
||||||
|
import SupportIcon from './icons/IconSupport.vue'
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<template>
|
||||||
|
<div>aaa</div>
|
||||||
|
</template>
|
87
src/components/WelcomeItem.vue
Normal file
|
@ -0,0 +1,87 @@
|
||||||
|
<template>
|
||||||
|
<div class="item">
|
||||||
|
<i>
|
||||||
|
<slot name="icon"></slot>
|
||||||
|
</i>
|
||||||
|
<div class="details">
|
||||||
|
<h3>
|
||||||
|
<slot name="heading"></slot>
|
||||||
|
</h3>
|
||||||
|
<slot></slot>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</template>
|
||||||
|
|
||||||
|
<style scoped>
|
||||||
|
.item {
|
||||||
|
margin-top: 2rem;
|
||||||
|
display: flex;
|
||||||
|
position: relative;
|
||||||
|
}
|
||||||
|
|
||||||
|
.details {
|
||||||
|
flex: 1;
|
||||||
|
margin-left: 1rem;
|
||||||
|
}
|
||||||
|
|
||||||
|
i {
|
||||||
|
display: flex;
|
||||||
|
place-items: center;
|
||||||
|
place-content: center;
|
||||||
|
width: 32px;
|
||||||
|
height: 32px;
|
||||||
|
|
||||||
|
color: var(--color-text);
|
||||||
|
}
|
||||||
|
|
||||||
|
h3 {
|
||||||
|
font-size: 1.2rem;
|
||||||
|
font-weight: 500;
|
||||||
|
margin-bottom: 0.4rem;
|
||||||
|
color: var(--color-heading);
|
||||||
|
}
|
||||||
|
|
||||||
|
@media (min-width: 1024px) {
|
||||||
|
.item {
|
||||||
|
margin-top: 0;
|
||||||
|
padding: 0.4rem 0 1rem calc(var(--section-gap) / 2);
|
||||||
|
}
|
||||||
|
|
||||||
|
i {
|
||||||
|
top: calc(50% - 25px);
|
||||||
|
left: -26px;
|
||||||
|
position: absolute;
|
||||||
|
border: 1px solid var(--color-border);
|
||||||
|
background: var(--color-background);
|
||||||
|
border-radius: 8px;
|
||||||
|
width: 50px;
|
||||||
|
height: 50px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.item:before {
|
||||||
|
content: ' ';
|
||||||
|
border-left: 1px solid var(--color-border);
|
||||||
|
position: absolute;
|
||||||
|
left: 0;
|
||||||
|
bottom: calc(50% + 25px);
|
||||||
|
height: calc(50% - 25px);
|
||||||
|
}
|
||||||
|
|
||||||
|
.item:after {
|
||||||
|
content: ' ';
|
||||||
|
border-left: 1px solid var(--color-border);
|
||||||
|
position: absolute;
|
||||||
|
left: 0;
|
||||||
|
top: calc(50% + 25px);
|
||||||
|
height: calc(50% - 25px);
|
||||||
|
}
|
||||||
|
|
||||||
|
.item:first-of-type:before {
|
||||||
|
display: none;
|
||||||
|
}
|
||||||
|
|
||||||
|
.item:last-of-type:after {
|
||||||
|
display: none;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
</style>
|
171
src/components/dialog/Dialog.ts
Normal file
|
@ -0,0 +1,171 @@
|
||||||
|
import { EditorComponent, EDITOR_COMPONENT } from '@hufe921/canvas-editor'
|
||||||
|
import './dialog.css'
|
||||||
|
|
||||||
|
export interface IDialogData {
|
||||||
|
type: string
|
||||||
|
label?: string
|
||||||
|
name: string
|
||||||
|
value?: string
|
||||||
|
options?: { label: string; value: string }[]
|
||||||
|
placeholder?: string
|
||||||
|
width?: number
|
||||||
|
height?: number
|
||||||
|
required?: boolean
|
||||||
|
}
|
||||||
|
|
||||||
|
export interface IDialogConfirm {
|
||||||
|
name: string
|
||||||
|
value: string
|
||||||
|
}
|
||||||
|
|
||||||
|
export interface IDialogOptions {
|
||||||
|
onClose?: () => void
|
||||||
|
onCancel?: () => void
|
||||||
|
onConfirm?: (payload: IDialogConfirm[]) => void
|
||||||
|
title: string
|
||||||
|
data: IDialogData[]
|
||||||
|
}
|
||||||
|
|
||||||
|
export class Dialog {
|
||||||
|
private options: IDialogOptions
|
||||||
|
private mask: HTMLDivElement | null
|
||||||
|
private container: HTMLDivElement | null
|
||||||
|
private inputList: (
|
||||||
|
| HTMLInputElement
|
||||||
|
| HTMLTextAreaElement
|
||||||
|
| HTMLSelectElement
|
||||||
|
)[]
|
||||||
|
|
||||||
|
constructor(options: IDialogOptions) {
|
||||||
|
this.options = options
|
||||||
|
this.mask = null
|
||||||
|
this.container = null
|
||||||
|
this.inputList = []
|
||||||
|
this._render()
|
||||||
|
}
|
||||||
|
|
||||||
|
private _render() {
|
||||||
|
const { title, data, onClose, onCancel, onConfirm } = this.options
|
||||||
|
// 渲染遮罩层
|
||||||
|
const mask = document.createElement('div')
|
||||||
|
mask.classList.add('dialog-mask')
|
||||||
|
mask.setAttribute(EDITOR_COMPONENT, EditorComponent.COMPONENT)
|
||||||
|
document.body.append(mask)
|
||||||
|
// 渲染容器
|
||||||
|
const container = document.createElement('div')
|
||||||
|
container.classList.add('dialog-container')
|
||||||
|
container.setAttribute(EDITOR_COMPONENT, EditorComponent.COMPONENT)
|
||||||
|
// 弹窗
|
||||||
|
const dialogContainer = document.createElement('div')
|
||||||
|
dialogContainer.classList.add('dialog')
|
||||||
|
container.append(dialogContainer)
|
||||||
|
// 标题容器
|
||||||
|
const titleContainer = document.createElement('div')
|
||||||
|
titleContainer.classList.add('dialog-title')
|
||||||
|
// 标题&关闭按钮
|
||||||
|
const titleSpan = document.createElement('span')
|
||||||
|
titleSpan.append(document.createTextNode(title))
|
||||||
|
const titleClose = document.createElement('i')
|
||||||
|
titleClose.onclick = () => {
|
||||||
|
if (onClose) {
|
||||||
|
onClose()
|
||||||
|
}
|
||||||
|
this._dispose()
|
||||||
|
}
|
||||||
|
titleContainer.append(titleSpan)
|
||||||
|
titleContainer.append(titleClose)
|
||||||
|
dialogContainer.append(titleContainer)
|
||||||
|
// 选项容器
|
||||||
|
const optionContainer = document.createElement('div')
|
||||||
|
optionContainer.classList.add('dialog-option')
|
||||||
|
// 选项
|
||||||
|
for (let i = 0; i < data.length; i++) {
|
||||||
|
const option = data[i]
|
||||||
|
const optionItemContainer = document.createElement('div')
|
||||||
|
optionItemContainer.classList.add('dialog-option__item')
|
||||||
|
// 选项名称
|
||||||
|
if (option.label) {
|
||||||
|
const optionName = document.createElement('span')
|
||||||
|
optionName.append(document.createTextNode(option.label))
|
||||||
|
optionItemContainer.append(optionName)
|
||||||
|
if (option.required) {
|
||||||
|
optionName.classList.add('dialog-option__item--require')
|
||||||
|
}
|
||||||
|
}
|
||||||
|
// 选项输入框
|
||||||
|
let optionInput:
|
||||||
|
| HTMLInputElement
|
||||||
|
| HTMLTextAreaElement
|
||||||
|
| HTMLSelectElement
|
||||||
|
if (option.type === 'select') {
|
||||||
|
optionInput = document.createElement('select')
|
||||||
|
option.options?.forEach(item => {
|
||||||
|
const optionItem = document.createElement('option')
|
||||||
|
optionItem.value = item.value
|
||||||
|
optionItem.label = item.label
|
||||||
|
optionInput.append(optionItem)
|
||||||
|
})
|
||||||
|
} else if (option.type === 'textarea') {
|
||||||
|
optionInput = document.createElement('textarea')
|
||||||
|
} else {
|
||||||
|
optionInput = document.createElement('input')
|
||||||
|
optionInput.type = option.type
|
||||||
|
}
|
||||||
|
if (option.width) {
|
||||||
|
optionInput.style.width = `${option.width}px`
|
||||||
|
}
|
||||||
|
if (option.height) {
|
||||||
|
optionInput.style.height = `${option.height}px`
|
||||||
|
}
|
||||||
|
optionInput.name = option.name
|
||||||
|
optionInput.value = option.value || ''
|
||||||
|
if (!(optionInput instanceof HTMLSelectElement)) {
|
||||||
|
optionInput.placeholder = option.placeholder || ''
|
||||||
|
}
|
||||||
|
optionItemContainer.append(optionInput)
|
||||||
|
optionContainer.append(optionItemContainer)
|
||||||
|
this.inputList.push(optionInput)
|
||||||
|
}
|
||||||
|
dialogContainer.append(optionContainer)
|
||||||
|
// 按钮容器
|
||||||
|
const menuContainer = document.createElement('div')
|
||||||
|
menuContainer.classList.add('dialog-menu')
|
||||||
|
// 取消按钮
|
||||||
|
const cancelBtn = document.createElement('button')
|
||||||
|
cancelBtn.classList.add('dialog-menu__cancel')
|
||||||
|
cancelBtn.append(document.createTextNode('取消'))
|
||||||
|
cancelBtn.type = 'button'
|
||||||
|
cancelBtn.onclick = () => {
|
||||||
|
if (onCancel) {
|
||||||
|
onCancel()
|
||||||
|
}
|
||||||
|
this._dispose()
|
||||||
|
}
|
||||||
|
menuContainer.append(cancelBtn)
|
||||||
|
// 确认按钮
|
||||||
|
const confirmBtn = document.createElement('button')
|
||||||
|
confirmBtn.append(document.createTextNode('确定'))
|
||||||
|
confirmBtn.type = 'submit'
|
||||||
|
confirmBtn.onclick = () => {
|
||||||
|
if (onConfirm) {
|
||||||
|
const payload = this.inputList.map<IDialogConfirm>(input => ({
|
||||||
|
name: input.name,
|
||||||
|
value: input.value
|
||||||
|
}))
|
||||||
|
onConfirm(payload)
|
||||||
|
}
|
||||||
|
this._dispose()
|
||||||
|
}
|
||||||
|
menuContainer.append(confirmBtn)
|
||||||
|
dialogContainer.append(menuContainer)
|
||||||
|
// 渲染
|
||||||
|
document.body.append(container)
|
||||||
|
this.container = container
|
||||||
|
this.mask = mask
|
||||||
|
}
|
||||||
|
|
||||||
|
private _dispose() {
|
||||||
|
this.mask?.remove()
|
||||||
|
this.container?.remove()
|
||||||
|
}
|
||||||
|
}
|
131
src/components/dialog/dialog.css
Normal file
|
@ -0,0 +1,131 @@
|
||||||
|
.dialog-mask {
|
||||||
|
position: fixed;
|
||||||
|
left: 0;
|
||||||
|
top: 0;
|
||||||
|
width: 100%;
|
||||||
|
height: 100%;
|
||||||
|
opacity: .5;
|
||||||
|
background: #000000;
|
||||||
|
z-index: 99;
|
||||||
|
}
|
||||||
|
|
||||||
|
.dialog-container {
|
||||||
|
position: fixed;
|
||||||
|
top: 0;
|
||||||
|
right: 0;
|
||||||
|
bottom: 0;
|
||||||
|
left: 0;
|
||||||
|
overflow: auto;
|
||||||
|
z-index: 999;
|
||||||
|
margin: 0;
|
||||||
|
display: flex;
|
||||||
|
justify-content: center;
|
||||||
|
align-items: center;
|
||||||
|
}
|
||||||
|
|
||||||
|
.dialog {
|
||||||
|
position: absolute;
|
||||||
|
padding: 0 30px 30px;
|
||||||
|
background: #ffffff;
|
||||||
|
box-shadow: 0 2px 12px 0 rgb(56 56 56 / 20%);
|
||||||
|
border: 1px solid #e2e6ed;
|
||||||
|
border-radius: 2px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.dialog-title {
|
||||||
|
position: relative;
|
||||||
|
border-bottom: 1px solid #e2e6ed;
|
||||||
|
margin-bottom: 30px;
|
||||||
|
height: 60px;
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
justify-content: space-between;
|
||||||
|
}
|
||||||
|
|
||||||
|
.dialog-title i {
|
||||||
|
width: 16px;
|
||||||
|
height: 16px;
|
||||||
|
cursor: pointer;
|
||||||
|
display: inline-block;
|
||||||
|
background: url(../../assets/images/close.svg);
|
||||||
|
}
|
||||||
|
|
||||||
|
.dialog-option__item {
|
||||||
|
margin-bottom: 18px;
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
justify-content: space-between;
|
||||||
|
}
|
||||||
|
|
||||||
|
.dialog-option__item span {
|
||||||
|
margin-right: 12px;
|
||||||
|
font-size: 14px;
|
||||||
|
color: #3d4757;
|
||||||
|
position: relative;
|
||||||
|
}
|
||||||
|
|
||||||
|
.dialog-option__item input,
|
||||||
|
.dialog-option__item textarea,
|
||||||
|
.dialog-option__item select {
|
||||||
|
width: 276px;
|
||||||
|
height: 30px;
|
||||||
|
border-radius: 2px;
|
||||||
|
border: 1px solid #d3d3d3;
|
||||||
|
min-height: 30px;
|
||||||
|
padding: 5px;
|
||||||
|
box-sizing: border-box;
|
||||||
|
outline: none;
|
||||||
|
appearance: none;
|
||||||
|
user-select: none;
|
||||||
|
font-family: inherit;
|
||||||
|
}
|
||||||
|
|
||||||
|
.dialog-option__item input:focus,
|
||||||
|
.dialog-option__item textarea:focus {
|
||||||
|
border-color: #4991f2;
|
||||||
|
}
|
||||||
|
|
||||||
|
.dialog-option__item--require::before {
|
||||||
|
content: "*";
|
||||||
|
color: #f56c6c;
|
||||||
|
margin-right: 4px;
|
||||||
|
position: absolute;
|
||||||
|
left: -8px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.dialog-menu {
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
justify-content: flex-end;
|
||||||
|
}
|
||||||
|
|
||||||
|
.dialog-menu button {
|
||||||
|
position: relative;
|
||||||
|
display: inline-block;
|
||||||
|
border: 1px solid #e2e6ed;
|
||||||
|
border-radius: 2px;
|
||||||
|
background: #ffffff;
|
||||||
|
line-height: 22px;
|
||||||
|
padding: 0 16px;
|
||||||
|
white-space: nowrap;
|
||||||
|
cursor: pointer;
|
||||||
|
}
|
||||||
|
|
||||||
|
.dialog-menu button:hover {
|
||||||
|
background: rgba(25, 55, 88, .04);
|
||||||
|
}
|
||||||
|
|
||||||
|
.dialog-menu__cancel {
|
||||||
|
margin-right: 16px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.dialog-menu button[type='submit'] {
|
||||||
|
color: #ffffff;
|
||||||
|
background: #4991f2;
|
||||||
|
border-color: #4991f2;
|
||||||
|
}
|
||||||
|
|
||||||
|
.dialog-menu button[type='submit']:hover {
|
||||||
|
background: #5b9cf3;
|
||||||
|
border-color: #5b9cf3;
|
||||||
|
}
|
7
src/components/icons/IconCommunity.vue
Normal file
|
@ -0,0 +1,7 @@
|
||||||
|
<template>
|
||||||
|
<svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" fill="currentColor">
|
||||||
|
<path
|
||||||
|
d="M15 4a1 1 0 1 0 0 2V4zm0 11v-1a1 1 0 0 0-1 1h1zm0 4l-.707.707A1 1 0 0 0 16 19h-1zm-4-4l.707-.707A1 1 0 0 0 11 14v1zm-4.707-1.293a1 1 0 0 0-1.414 1.414l1.414-1.414zm-.707.707l-.707-.707.707.707zM9 11v-1a1 1 0 0 0-.707.293L9 11zm-4 0h1a1 1 0 0 0-1-1v1zm0 4H4a1 1 0 0 0 1.707.707L5 15zm10-9h2V4h-2v2zm2 0a1 1 0 0 1 1 1h2a3 3 0 0 0-3-3v2zm1 1v6h2V7h-2zm0 6a1 1 0 0 1-1 1v2a3 3 0 0 0 3-3h-2zm-1 1h-2v2h2v-2zm-3 1v4h2v-4h-2zm1.707 3.293l-4-4-1.414 1.414 4 4 1.414-1.414zM11 14H7v2h4v-2zm-4 0c-.276 0-.525-.111-.707-.293l-1.414 1.414C5.42 15.663 6.172 16 7 16v-2zm-.707 1.121l3.414-3.414-1.414-1.414-3.414 3.414 1.414 1.414zM9 12h4v-2H9v2zm4 0a3 3 0 0 0 3-3h-2a1 1 0 0 1-1 1v2zm3-3V3h-2v6h2zm0-6a3 3 0 0 0-3-3v2a1 1 0 0 1 1 1h2zm-3-3H3v2h10V0zM3 0a3 3 0 0 0-3 3h2a1 1 0 0 1 1-1V0zM0 3v6h2V3H0zm0 6a3 3 0 0 0 3 3v-2a1 1 0 0 1-1-1H0zm3 3h2v-2H3v2zm1-1v4h2v-4H4zm1.707 4.707l.586-.586-1.414-1.414-.586.586 1.414 1.414z"
|
||||||
|
/>
|
||||||
|
</svg>
|
||||||
|
</template>
|
7
src/components/icons/IconDocumentation.vue
Normal file
|
@ -0,0 +1,7 @@
|
||||||
|
<template>
|
||||||
|
<svg xmlns="http://www.w3.org/2000/svg" width="20" height="17" fill="currentColor">
|
||||||
|
<path
|
||||||
|
d="M11 2.253a1 1 0 1 0-2 0h2zm-2 13a1 1 0 1 0 2 0H9zm.447-12.167a1 1 0 1 0 1.107-1.666L9.447 3.086zM1 2.253L.447 1.42A1 1 0 0 0 0 2.253h1zm0 13H0a1 1 0 0 0 1.553.833L1 15.253zm8.447.833a1 1 0 1 0 1.107-1.666l-1.107 1.666zm0-14.666a1 1 0 1 0 1.107 1.666L9.447 1.42zM19 2.253h1a1 1 0 0 0-.447-.833L19 2.253zm0 13l-.553.833A1 1 0 0 0 20 15.253h-1zm-9.553-.833a1 1 0 1 0 1.107 1.666L9.447 14.42zM9 2.253v13h2v-13H9zm1.553-.833C9.203.523 7.42 0 5.5 0v2c1.572 0 2.961.431 3.947 1.086l1.107-1.666zM5.5 0C3.58 0 1.797.523.447 1.42l1.107 1.666C2.539 2.431 3.928 2 5.5 2V0zM0 2.253v13h2v-13H0zm1.553 13.833C2.539 15.431 3.928 15 5.5 15v-2c-1.92 0-3.703.523-5.053 1.42l1.107 1.666zM5.5 15c1.572 0 2.961.431 3.947 1.086l1.107-1.666C9.203 13.523 7.42 13 5.5 13v2zm5.053-11.914C11.539 2.431 12.928 2 14.5 2V0c-1.92 0-3.703.523-5.053 1.42l1.107 1.666zM14.5 2c1.573 0 2.961.431 3.947 1.086l1.107-1.666C18.203.523 16.421 0 14.5 0v2zm3.5.253v13h2v-13h-2zm1.553 12.167C18.203 13.523 16.421 13 14.5 13v2c1.573 0 2.961.431 3.947 1.086l1.107-1.666zM14.5 13c-1.92 0-3.703.523-5.053 1.42l1.107 1.666C11.539 15.431 12.928 15 14.5 15v-2z"
|
||||||
|
/>
|
||||||
|
</svg>
|
||||||
|
</template>
|
7
src/components/icons/IconEcosystem.vue
Normal file
|
@ -0,0 +1,7 @@
|
||||||
|
<template>
|
||||||
|
<svg xmlns="http://www.w3.org/2000/svg" width="18" height="20" fill="currentColor">
|
||||||
|
<path
|
||||||
|
d="M11.447 8.894a1 1 0 1 0-.894-1.789l.894 1.789zm-2.894-.789a1 1 0 1 0 .894 1.789l-.894-1.789zm0 1.789a1 1 0 1 0 .894-1.789l-.894 1.789zM7.447 7.106a1 1 0 1 0-.894 1.789l.894-1.789zM10 9a1 1 0 1 0-2 0h2zm-2 2.5a1 1 0 1 0 2 0H8zm9.447-5.606a1 1 0 1 0-.894-1.789l.894 1.789zm-2.894-.789a1 1 0 1 0 .894 1.789l-.894-1.789zm2 .789a1 1 0 1 0 .894-1.789l-.894 1.789zm-1.106-2.789a1 1 0 1 0-.894 1.789l.894-1.789zM18 5a1 1 0 1 0-2 0h2zm-2 2.5a1 1 0 1 0 2 0h-2zm-5.447-4.606a1 1 0 1 0 .894-1.789l-.894 1.789zM9 1l.447-.894a1 1 0 0 0-.894 0L9 1zm-2.447.106a1 1 0 1 0 .894 1.789l-.894-1.789zm-6 3a1 1 0 1 0 .894 1.789L.553 4.106zm2.894.789a1 1 0 1 0-.894-1.789l.894 1.789zm-2-.789a1 1 0 1 0-.894 1.789l.894-1.789zm1.106 2.789a1 1 0 1 0 .894-1.789l-.894 1.789zM2 5a1 1 0 1 0-2 0h2zM0 7.5a1 1 0 1 0 2 0H0zm8.553 12.394a1 1 0 1 0 .894-1.789l-.894 1.789zm-1.106-2.789a1 1 0 1 0-.894 1.789l.894-1.789zm1.106 1a1 1 0 1 0 .894 1.789l-.894-1.789zm2.894.789a1 1 0 1 0-.894-1.789l.894 1.789zM8 19a1 1 0 1 0 2 0H8zm2-2.5a1 1 0 1 0-2 0h2zm-7.447.394a1 1 0 1 0 .894-1.789l-.894 1.789zM1 15H0a1 1 0 0 0 .553.894L1 15zm1-2.5a1 1 0 1 0-2 0h2zm12.553 2.606a1 1 0 1 0 .894 1.789l-.894-1.789zM17 15l.447.894A1 1 0 0 0 18 15h-1zm1-2.5a1 1 0 1 0-2 0h2zm-7.447-5.394l-2 1 .894 1.789 2-1-.894-1.789zm-1.106 1l-2-1-.894 1.789 2 1 .894-1.789zM8 9v2.5h2V9H8zm8.553-4.894l-2 1 .894 1.789 2-1-.894-1.789zm.894 0l-2-1-.894 1.789 2 1 .894-1.789zM16 5v2.5h2V5h-2zm-4.553-3.894l-2-1-.894 1.789 2 1 .894-1.789zm-2.894-1l-2 1 .894 1.789 2-1L8.553.106zM1.447 5.894l2-1-.894-1.789-2 1 .894 1.789zm-.894 0l2 1 .894-1.789-2-1-.894 1.789zM0 5v2.5h2V5H0zm9.447 13.106l-2-1-.894 1.789 2 1 .894-1.789zm0 1.789l2-1-.894-1.789-2 1 .894 1.789zM10 19v-2.5H8V19h2zm-6.553-3.894l-2-1-.894 1.789 2 1 .894-1.789zM2 15v-2.5H0V15h2zm13.447 1.894l2-1-.894-1.789-2 1 .894 1.789zM18 15v-2.5h-2V15h2z"
|
||||||
|
/>
|
||||||
|
</svg>
|
||||||
|
</template>
|
7
src/components/icons/IconSupport.vue
Normal file
|
@ -0,0 +1,7 @@
|
||||||
|
<template>
|
||||||
|
<svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" fill="currentColor">
|
||||||
|
<path
|
||||||
|
d="M10 3.22l-.61-.6a5.5 5.5 0 0 0-7.666.105 5.5 5.5 0 0 0-.114 7.665L10 18.78l8.39-8.4a5.5 5.5 0 0 0-.114-7.665 5.5 5.5 0 0 0-7.666-.105l-.61.61z"
|
||||||
|
/>
|
||||||
|
</svg>
|
||||||
|
</template>
|
19
src/components/icons/IconTooling.vue
Normal file
|
@ -0,0 +1,19 @@
|
||||||
|
<!-- This icon is from <https://github.com/Templarian/MaterialDesign>, distributed under Apache 2.0 (https://www.apache.org/licenses/LICENSE-2.0) license-->
|
||||||
|
<template>
|
||||||
|
<svg
|
||||||
|
xmlns="http://www.w3.org/2000/svg"
|
||||||
|
xmlns:xlink="http://www.w3.org/1999/xlink"
|
||||||
|
aria-hidden="true"
|
||||||
|
role="img"
|
||||||
|
class="iconify iconify--mdi"
|
||||||
|
width="24"
|
||||||
|
height="24"
|
||||||
|
preserveAspectRatio="xMidYMid meet"
|
||||||
|
viewBox="0 0 24 24"
|
||||||
|
>
|
||||||
|
<path
|
||||||
|
d="M20 18v-4h-3v1h-2v-1H9v1H7v-1H4v4h16M6.33 8l-1.74 4H7v-1h2v1h6v-1h2v1h2.41l-1.74-4H6.33M9 5v1h6V5H9m12.84 7.61c.1.22.16.48.16.8V18c0 .53-.21 1-.6 1.41c-.4.4-.85.59-1.4.59H4c-.55 0-1-.19-1.4-.59C2.21 19 2 18.53 2 18v-4.59c0-.32.06-.58.16-.8L4.5 7.22C4.84 6.41 5.45 6 6.33 6H7V5c0-.55.18-1 .57-1.41C7.96 3.2 8.44 3 9 3h6c.56 0 1.04.2 1.43.59c.39.41.57.86.57 1.41v1h.67c.88 0 1.49.41 1.83 1.22l2.34 5.39z"
|
||||||
|
fill="currentColor"
|
||||||
|
></path>
|
||||||
|
</svg>
|
||||||
|
</template>
|
309
src/components/signature/Signature.ts
Normal file
|
@ -0,0 +1,309 @@
|
||||||
|
import { EditorComponent, EDITOR_COMPONENT } from '@hufe921/canvas-editor'
|
||||||
|
import './signature.css'
|
||||||
|
|
||||||
|
export interface ISignatureResult {
|
||||||
|
value: string
|
||||||
|
width: number
|
||||||
|
height: number
|
||||||
|
}
|
||||||
|
|
||||||
|
export interface ISignatureOptions {
|
||||||
|
width?: number
|
||||||
|
height?: number
|
||||||
|
onClose?: () => void
|
||||||
|
onCancel?: () => void
|
||||||
|
onConfirm?: (payload: ISignatureResult | null) => void
|
||||||
|
}
|
||||||
|
|
||||||
|
export class Signature {
|
||||||
|
private readonly MAX_RECORD_COUNT = 1000
|
||||||
|
private readonly DEFAULT_WIDTH = 390
|
||||||
|
private readonly DEFAULT_HEIGHT = 180
|
||||||
|
private undoStack: Array<Function> = []
|
||||||
|
private x = 0
|
||||||
|
private y = 0
|
||||||
|
private isDrawing = false
|
||||||
|
private isDrawn = false
|
||||||
|
private linePoints: [number, number][] = []
|
||||||
|
private canvasWidth: number
|
||||||
|
private canvasHeight: number
|
||||||
|
private options: ISignatureOptions
|
||||||
|
private mask: HTMLDivElement
|
||||||
|
private container: HTMLDivElement
|
||||||
|
private trashContainer: HTMLDivElement
|
||||||
|
private undoContainer: HTMLDivElement
|
||||||
|
private canvas: HTMLCanvasElement
|
||||||
|
private ctx: CanvasRenderingContext2D
|
||||||
|
private preTimeStamp: number
|
||||||
|
private dpr: number
|
||||||
|
|
||||||
|
constructor(options: ISignatureOptions) {
|
||||||
|
this.options = options
|
||||||
|
this.preTimeStamp = 0
|
||||||
|
this.dpr = window.devicePixelRatio
|
||||||
|
this.canvasWidth = (options.width || this.DEFAULT_WIDTH) * this.dpr
|
||||||
|
this.canvasHeight = (options.height || this.DEFAULT_HEIGHT) * this.dpr
|
||||||
|
const { mask, container, trashContainer, undoContainer, canvas } =
|
||||||
|
this._render()
|
||||||
|
this.mask = mask
|
||||||
|
this.container = container
|
||||||
|
this.trashContainer = trashContainer
|
||||||
|
this.undoContainer = undoContainer
|
||||||
|
this.canvas = canvas
|
||||||
|
this.ctx = <CanvasRenderingContext2D>canvas.getContext('2d')
|
||||||
|
this.ctx.scale(this.dpr, this.dpr)
|
||||||
|
this.ctx.lineCap = 'round'
|
||||||
|
this._bindEvent()
|
||||||
|
this._clearUndoFn()
|
||||||
|
}
|
||||||
|
|
||||||
|
private _render() {
|
||||||
|
const { onClose, onCancel, onConfirm } = this.options
|
||||||
|
// 渲染遮罩层
|
||||||
|
const mask = document.createElement('div')
|
||||||
|
mask.classList.add('signature-mask')
|
||||||
|
mask.setAttribute(EDITOR_COMPONENT, EditorComponent.COMPONENT)
|
||||||
|
document.body.append(mask)
|
||||||
|
// 渲染容器
|
||||||
|
const container = document.createElement('div')
|
||||||
|
container.classList.add('signature-container')
|
||||||
|
container.setAttribute(EDITOR_COMPONENT, EditorComponent.COMPONENT)
|
||||||
|
// 弹窗
|
||||||
|
const signatureContainer = document.createElement('div')
|
||||||
|
signatureContainer.classList.add('signature')
|
||||||
|
container.append(signatureContainer)
|
||||||
|
// 标题容器
|
||||||
|
const titleContainer = document.createElement('div')
|
||||||
|
titleContainer.classList.add('signature-title')
|
||||||
|
// 标题&关闭按钮
|
||||||
|
const titleSpan = document.createElement('span')
|
||||||
|
titleSpan.append(document.createTextNode('插入签名'))
|
||||||
|
const titleClose = document.createElement('i')
|
||||||
|
titleClose.onclick = () => {
|
||||||
|
if (onClose) {
|
||||||
|
onClose()
|
||||||
|
}
|
||||||
|
this._dispose()
|
||||||
|
}
|
||||||
|
titleContainer.append(titleSpan)
|
||||||
|
titleContainer.append(titleClose)
|
||||||
|
signatureContainer.append(titleContainer)
|
||||||
|
// 操作区
|
||||||
|
const operationContainer = document.createElement('div')
|
||||||
|
operationContainer.classList.add('signature-operation')
|
||||||
|
// 撤销
|
||||||
|
const undoContainer = document.createElement('div')
|
||||||
|
undoContainer.classList.add('signature-operation__undo')
|
||||||
|
const undoIcon = document.createElement('i')
|
||||||
|
const undoLabel = document.createElement('span')
|
||||||
|
undoLabel.innerText = '撤销'
|
||||||
|
undoContainer.append(undoIcon)
|
||||||
|
undoContainer.append(undoLabel)
|
||||||
|
operationContainer.append(undoContainer)
|
||||||
|
// 清空画布
|
||||||
|
const trashContainer = document.createElement('div')
|
||||||
|
trashContainer.classList.add('signature-operation__trash')
|
||||||
|
const trashIcon = document.createElement('i')
|
||||||
|
const trashLabel = document.createElement('span')
|
||||||
|
trashLabel.innerText = '清空'
|
||||||
|
trashContainer.append(trashIcon)
|
||||||
|
trashContainer.append(trashLabel)
|
||||||
|
operationContainer.append(trashContainer)
|
||||||
|
signatureContainer.append(operationContainer)
|
||||||
|
// 绘图区
|
||||||
|
const canvasContainer = document.createElement('div')
|
||||||
|
canvasContainer.classList.add('signature-canvas')
|
||||||
|
const canvas = document.createElement('canvas')
|
||||||
|
canvas.width = this.canvasWidth
|
||||||
|
canvas.height = this.canvasHeight
|
||||||
|
canvas.style.width = `${this.canvasWidth / this.dpr}px`
|
||||||
|
canvas.style.height = `${this.canvasHeight / this.dpr}px`
|
||||||
|
canvasContainer.append(canvas)
|
||||||
|
signatureContainer.append(canvasContainer)
|
||||||
|
// 按钮容器
|
||||||
|
const menuContainer = document.createElement('div')
|
||||||
|
menuContainer.classList.add('signature-menu')
|
||||||
|
// 取消按钮
|
||||||
|
const cancelBtn = document.createElement('button')
|
||||||
|
cancelBtn.classList.add('signature-menu__cancel')
|
||||||
|
cancelBtn.append(document.createTextNode('取消'))
|
||||||
|
cancelBtn.type = 'button'
|
||||||
|
cancelBtn.onclick = () => {
|
||||||
|
if (onCancel) {
|
||||||
|
onCancel()
|
||||||
|
}
|
||||||
|
this._dispose()
|
||||||
|
}
|
||||||
|
menuContainer.append(cancelBtn)
|
||||||
|
// 确认按钮
|
||||||
|
const confirmBtn = document.createElement('button')
|
||||||
|
confirmBtn.append(document.createTextNode('确定'))
|
||||||
|
confirmBtn.type = 'submit'
|
||||||
|
confirmBtn.onclick = () => {
|
||||||
|
if (onConfirm) {
|
||||||
|
onConfirm(this._toData())
|
||||||
|
}
|
||||||
|
this._dispose()
|
||||||
|
}
|
||||||
|
menuContainer.append(confirmBtn)
|
||||||
|
signatureContainer.append(menuContainer)
|
||||||
|
// 渲染
|
||||||
|
document.body.append(container)
|
||||||
|
this.container = container
|
||||||
|
this.mask = mask
|
||||||
|
return {
|
||||||
|
mask,
|
||||||
|
canvas,
|
||||||
|
container,
|
||||||
|
trashContainer,
|
||||||
|
undoContainer
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private _bindEvent() {
|
||||||
|
this.trashContainer.onclick = this._clearCanvas.bind(this)
|
||||||
|
this.undoContainer.onclick = this._undo.bind(this)
|
||||||
|
this.canvas.onmousedown = this._startDraw.bind(this)
|
||||||
|
this.canvas.onmousemove = this._draw.bind(this)
|
||||||
|
this.container.onmouseup = this._stopDraw.bind(this)
|
||||||
|
}
|
||||||
|
|
||||||
|
private _undo() {
|
||||||
|
if (this.undoStack.length > 1) {
|
||||||
|
this.undoStack.pop()
|
||||||
|
if (this.undoStack.length) {
|
||||||
|
this.undoStack[this.undoStack.length - 1]()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private _saveUndoFn(fn: Function) {
|
||||||
|
this.undoStack.push(fn)
|
||||||
|
while (this.undoStack.length > this.MAX_RECORD_COUNT) {
|
||||||
|
this.undoStack.shift()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private _clearUndoFn() {
|
||||||
|
const clearFn = () => {
|
||||||
|
this.ctx.clearRect(0, 0, this.canvasWidth, this.canvasHeight)
|
||||||
|
}
|
||||||
|
this.undoStack = [clearFn]
|
||||||
|
}
|
||||||
|
|
||||||
|
private _clearCanvas() {
|
||||||
|
this._clearUndoFn()
|
||||||
|
this.ctx.clearRect(0, 0, this.canvasWidth, this.canvasHeight)
|
||||||
|
}
|
||||||
|
|
||||||
|
private _startDraw(evt: MouseEvent) {
|
||||||
|
this.isDrawing = true
|
||||||
|
this.x = evt.offsetX
|
||||||
|
this.y = evt.offsetY
|
||||||
|
this.ctx.lineWidth = 1
|
||||||
|
}
|
||||||
|
|
||||||
|
private _draw(evt: MouseEvent) {
|
||||||
|
if (!this.isDrawing) return
|
||||||
|
// 计算鼠标移动速度
|
||||||
|
const curTimestamp = performance.now()
|
||||||
|
const distance = Math.sqrt(evt.movementX ** 2 + evt.movementY ** 2)
|
||||||
|
const speed = distance / (curTimestamp - this.preTimeStamp)
|
||||||
|
// 目标线宽:最小速度1,最大速度5,系数3
|
||||||
|
const SPEED_FACTOR = 3
|
||||||
|
const targetLineWidth = Math.min(5, Math.max(1, 5 - speed * SPEED_FACTOR))
|
||||||
|
// 平滑过渡算法(20%的变化比例)调整线条粗细:系数0.2
|
||||||
|
const SMOOTH_FACTOR = 0.2
|
||||||
|
this.ctx.lineWidth =
|
||||||
|
this.ctx.lineWidth * (1 - SMOOTH_FACTOR) + targetLineWidth * SMOOTH_FACTOR
|
||||||
|
// 绘制
|
||||||
|
const { offsetX, offsetY } = evt
|
||||||
|
this.ctx.beginPath()
|
||||||
|
this.ctx.moveTo(this.x, this.y)
|
||||||
|
this.ctx.lineTo(offsetX, offsetY)
|
||||||
|
this.ctx.stroke()
|
||||||
|
this.x = offsetX
|
||||||
|
this.y = offsetY
|
||||||
|
this.linePoints.push([offsetX, offsetY])
|
||||||
|
this.isDrawn = true
|
||||||
|
// 缓存之前时间戳
|
||||||
|
this.preTimeStamp = curTimestamp
|
||||||
|
}
|
||||||
|
|
||||||
|
private _stopDraw() {
|
||||||
|
this.isDrawing = false
|
||||||
|
if (this.isDrawn) {
|
||||||
|
const imageData = this.ctx.getImageData(
|
||||||
|
0,
|
||||||
|
0,
|
||||||
|
this.canvasWidth,
|
||||||
|
this.canvasHeight
|
||||||
|
)
|
||||||
|
const self = this
|
||||||
|
this._saveUndoFn(function () {
|
||||||
|
self.ctx.clearRect(0, 0, self.canvasWidth, self.canvasHeight)
|
||||||
|
self.ctx.putImageData(imageData, 0, 0)
|
||||||
|
})
|
||||||
|
this.isDrawn = false
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private _toData(): ISignatureResult | null {
|
||||||
|
if (!this.linePoints.length) return null
|
||||||
|
// 查找矩形四角坐标
|
||||||
|
const startX = this.linePoints[0][0]
|
||||||
|
const startY = this.linePoints[0][1]
|
||||||
|
let minX = startX
|
||||||
|
let minY = startY
|
||||||
|
let maxX = startX
|
||||||
|
let maxY = startY
|
||||||
|
for (let p = 0; p < this.linePoints.length; p++) {
|
||||||
|
const point = this.linePoints[p]
|
||||||
|
if (minX > point[0]) {
|
||||||
|
minX = point[0]
|
||||||
|
}
|
||||||
|
if (maxX < point[0]) {
|
||||||
|
maxX = point[0]
|
||||||
|
}
|
||||||
|
if (minY > point[1]) {
|
||||||
|
minY = point[1]
|
||||||
|
}
|
||||||
|
if (maxY < point[1]) {
|
||||||
|
maxY = point[1]
|
||||||
|
}
|
||||||
|
}
|
||||||
|
// 增加边框宽度
|
||||||
|
const lineWidth = this.ctx.lineWidth
|
||||||
|
minX = minX < lineWidth ? 0 : minX - lineWidth
|
||||||
|
minY = minY < lineWidth ? 0 : minY - lineWidth
|
||||||
|
maxX = maxX + lineWidth
|
||||||
|
maxY = maxY + lineWidth
|
||||||
|
const sw = maxX - minX
|
||||||
|
const sh = maxY - minY
|
||||||
|
// 裁剪图像
|
||||||
|
const imageData = this.ctx.getImageData(
|
||||||
|
minX * this.dpr,
|
||||||
|
minY * this.dpr,
|
||||||
|
sw * this.dpr,
|
||||||
|
sh * this.dpr
|
||||||
|
)
|
||||||
|
const canvas = document.createElement('canvas')
|
||||||
|
canvas.style.width = `${sw}px`
|
||||||
|
canvas.style.height = `${sh}px`
|
||||||
|
canvas.width = sw * this.dpr
|
||||||
|
canvas.height = sh * this.dpr
|
||||||
|
const ctx = <CanvasRenderingContext2D>canvas.getContext('2d')!
|
||||||
|
ctx.putImageData(imageData, 0, 0)
|
||||||
|
const value = canvas.toDataURL()
|
||||||
|
return {
|
||||||
|
value,
|
||||||
|
width: sw,
|
||||||
|
height: sh
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private _dispose() {
|
||||||
|
this.mask.remove()
|
||||||
|
this.container.remove()
|
||||||
|
}
|
||||||
|
}
|
128
src/components/signature/signature.css
Normal file
|
@ -0,0 +1,128 @@
|
||||||
|
.signature-mask {
|
||||||
|
position: fixed;
|
||||||
|
left: 0;
|
||||||
|
top: 0;
|
||||||
|
width: 100%;
|
||||||
|
height: 100%;
|
||||||
|
opacity: .5;
|
||||||
|
background: #000000;
|
||||||
|
z-index: 99;
|
||||||
|
}
|
||||||
|
|
||||||
|
.signature-container {
|
||||||
|
position: fixed;
|
||||||
|
top: 0;
|
||||||
|
right: 0;
|
||||||
|
bottom: 0;
|
||||||
|
left: 0;
|
||||||
|
overflow: auto;
|
||||||
|
z-index: 999;
|
||||||
|
margin: 0;
|
||||||
|
display: flex;
|
||||||
|
justify-content: center;
|
||||||
|
align-items: center;
|
||||||
|
}
|
||||||
|
|
||||||
|
.signature {
|
||||||
|
position: absolute;
|
||||||
|
padding: 0 30px 30px;
|
||||||
|
background: #ffffff;
|
||||||
|
box-shadow: 0 2px 12px 0 rgb(56 56 56 / 20%);
|
||||||
|
border: 1px solid #e2e6ed;
|
||||||
|
border-radius: 2px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.signature-title {
|
||||||
|
position: relative;
|
||||||
|
border-bottom: 1px solid #e2e6ed;
|
||||||
|
margin-bottom: 15px;
|
||||||
|
height: 60px;
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
justify-content: space-between;
|
||||||
|
}
|
||||||
|
|
||||||
|
.signature-title i {
|
||||||
|
width: 16px;
|
||||||
|
height: 16px;
|
||||||
|
cursor: pointer;
|
||||||
|
display: inline-block;
|
||||||
|
background: url(../../assets/images/close.svg);
|
||||||
|
}
|
||||||
|
|
||||||
|
.signature-operation>div {
|
||||||
|
cursor: pointer;
|
||||||
|
display: inline-flex;
|
||||||
|
align-items: center;
|
||||||
|
color: #3d4757;
|
||||||
|
user-select: none;
|
||||||
|
}
|
||||||
|
|
||||||
|
.signature-operation>div:hover {
|
||||||
|
color: #6e7175;
|
||||||
|
}
|
||||||
|
|
||||||
|
.signature-operation>div i {
|
||||||
|
width: 24px;
|
||||||
|
height: 24px;
|
||||||
|
display: inline-block;
|
||||||
|
}
|
||||||
|
|
||||||
|
.signature-operation__undo {
|
||||||
|
background: url(../../assets/images/signature-undo.svg) no-repeat;
|
||||||
|
}
|
||||||
|
|
||||||
|
.signature-operation__trash {
|
||||||
|
background: url(../../assets/images/trash.svg) no-repeat;
|
||||||
|
}
|
||||||
|
|
||||||
|
.signature-operation>div span {
|
||||||
|
font-size: 12px;
|
||||||
|
margin: 0 5px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.signature-canvas {
|
||||||
|
margin: 15px 0;
|
||||||
|
user-select: none;
|
||||||
|
}
|
||||||
|
|
||||||
|
.signature-canvas canvas {
|
||||||
|
background: #f3f5f7;
|
||||||
|
}
|
||||||
|
|
||||||
|
.signature-menu {
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
justify-content: flex-end;
|
||||||
|
}
|
||||||
|
|
||||||
|
.signature-menu button {
|
||||||
|
position: relative;
|
||||||
|
display: inline-block;
|
||||||
|
border: 1px solid #e2e6ed;
|
||||||
|
border-radius: 2px;
|
||||||
|
background: #ffffff;
|
||||||
|
line-height: 22px;
|
||||||
|
padding: 0 16px;
|
||||||
|
white-space: nowrap;
|
||||||
|
cursor: pointer;
|
||||||
|
}
|
||||||
|
|
||||||
|
.signature-menu button:hover {
|
||||||
|
background: rgba(25, 55, 88, .04);
|
||||||
|
}
|
||||||
|
|
||||||
|
.signature-menu__cancel {
|
||||||
|
margin-right: 16px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.signature-menu button[type='submit'] {
|
||||||
|
color: #ffffff;
|
||||||
|
background: #4991f2;
|
||||||
|
border-color: #4991f2;
|
||||||
|
}
|
||||||
|
|
||||||
|
.signature-menu button[type='submit']:hover {
|
||||||
|
background: #5b9cf3;
|
||||||
|
border-color: #5b9cf3;
|
||||||
|
}
|
24
src/main.js
Normal file
|
@ -0,0 +1,24 @@
|
||||||
|
//import './assets/main.css'
|
||||||
|
import './assets/style.css'
|
||||||
|
import ElementPlus from 'element-plus'
|
||||||
|
import 'element-plus/dist/index.css'
|
||||||
|
import { createRouter, createWebHistory } from 'vue-router'
|
||||||
|
import { createApp } from 'vue'
|
||||||
|
|
||||||
|
import App from './App.vue'
|
||||||
|
import NewPage from './components/HelloWorld.vue'
|
||||||
|
const routes = [
|
||||||
|
{ path: '/', component: App },
|
||||||
|
{ path: '/new-page', component: NewPage }
|
||||||
|
]
|
||||||
|
|
||||||
|
const router = createRouter({
|
||||||
|
history: createWebHistory(),
|
||||||
|
routes
|
||||||
|
})
|
||||||
|
const app = createApp(App)
|
||||||
|
app.use(ElementPlus)
|
||||||
|
//app.provide('$axios',axios)
|
||||||
|
app.use(router)
|
||||||
|
app.mount('#app')
|
||||||
|
//createApp(App).use(ElementPlus,VueAxios, axios).mount('#app')
|
106
src/options.js
Normal file
|
@ -0,0 +1,106 @@
|
||||||
|
interface IEditorOption {
|
||||||
|
mode?: EditorMode // 编辑器模式:编辑、清洁(不显示视觉辅助元素。如:分页符)、只读、表单(仅控件内可编辑)、打印(不显示辅助元素、未书写控件及前后括号)。默认:编辑
|
||||||
|
defaultType?: string // 默认元素类型。默认:TEXT
|
||||||
|
defaultColor?: string // 默认字体颜色。默认:#000000
|
||||||
|
defaultFont?: string // 默认字体。默认:Microsoft YaHei
|
||||||
|
defaultSize?: number // 默认字号。默认:16
|
||||||
|
minSize?: number // 最小字号。默认:5
|
||||||
|
maxSize?: number // 最大字号。默认:72
|
||||||
|
defaultBasicRowMarginHeight?: number // 默认行高。默认:8
|
||||||
|
defaultRowMargin?: number // 默认行间距。默认:1
|
||||||
|
defaultTabWidth?: number // 默认tab宽度。默认:32
|
||||||
|
width?: number // 纸张宽度。默认:794
|
||||||
|
height?: number // 纸张高度。默认:1123
|
||||||
|
scale?: number // 缩放比例。默认:1
|
||||||
|
pageGap?: number // 纸张间隔。默认:20
|
||||||
|
underlineColor?: string // 下划线颜色。默认:#000000
|
||||||
|
strikeoutColor?: string // 删除线颜色。默认:#FF0000
|
||||||
|
rangeColor?: string // 选区颜色。默认:#AECBFA
|
||||||
|
rangeAlpha?: number // 选区透明度。默认:0.6
|
||||||
|
rangeMinWidth?: number // 选区最小宽度。默认:5
|
||||||
|
searchMatchColor?: string // 搜索高亮颜色。默认:#FFFF00
|
||||||
|
searchNavigateMatchColor?: string // 搜索导航高亮颜色。默认:#AAD280
|
||||||
|
searchMatchAlpha?: number // 搜索高亮透明度。默认:0.6
|
||||||
|
highlightAlpha?: number // 高亮元素透明度。默认:0.6
|
||||||
|
resizerColor?: string // 图片尺寸器颜色。默认:#4182D9
|
||||||
|
resizerSize?: number // 图片尺寸器大小。默认:5
|
||||||
|
marginIndicatorSize?: number // 页边距指示器长度。默认:35
|
||||||
|
marginIndicatorColor?: string // 页边距指示器颜色。默认:#BABABA
|
||||||
|
margins?: IMargin // 页面边距。默认:[100, 120, 100, 120]
|
||||||
|
pageMode?: PageMode // 纸张模式:连页、分页。默认:分页
|
||||||
|
defaultHyperlinkColor?: string // 默认超链接颜色。默认:#0000FF
|
||||||
|
table?: ITableOption // 表格配置。{tdPadding?:IPadding; defaultTrMinHeight?:number; defaultColMinWidth?:number}
|
||||||
|
header?: IHeader // 页眉信息。{top?:number; maxHeightRadio?:MaxHeightRatio;}
|
||||||
|
footer?: IFooter // 页脚信息。{bottom?:number; maxHeightRadio?:MaxHeightRatio;}
|
||||||
|
pageNumber?: IPageNumber // 页码信息。{bottom:number; size:number; font:string; color:string; rowFlex:RowFlex; format:string; numberType:NumberType;}
|
||||||
|
paperDirection?: PaperDirection // 纸张方向:纵向、横向
|
||||||
|
inactiveAlpha?: number // 正文内容失焦时透明度。默认值:0.6
|
||||||
|
historyMaxRecordCount?: number // 历史(撤销重做)最大记录次数。默认:100次
|
||||||
|
printPixelRatio?: number // 打印像素比率(值越大越清晰,但尺寸越大)。默认:3
|
||||||
|
maskMargin?: IMargin // 编辑器上的遮盖边距(如悬浮到编辑器上的菜单栏、底部工具栏)。默认:[0, 0, 0, 0]
|
||||||
|
letterClass?: string[] // 排版支持的字母类。默认:a-zA-Z。内置可选择的字母表类:LETTER_CLASS
|
||||||
|
contextMenuDisableKeys?: string[] // 禁用的右键菜单。默认:[]
|
||||||
|
scrollContainerSelector?: string // 滚动区域选择器。默认:document
|
||||||
|
wordBreak?: WordBreak // 单词与标点断行:BREAK_WORD首行不出现标点&单词不拆分、BREAK_ALL按字符宽度撑满后折行。默认:BREAK_WORD
|
||||||
|
watermark?: IWatermark // 水印信息。{data:string; color?:string; opacity?:number; size?:number; font?:string;}
|
||||||
|
control?: IControlOption // 控件信息。 {placeholderColor?:string; bracketColor?:string; prefix?:string; postfix?:string; borderWidth?: number; borderColor?: string;}
|
||||||
|
checkbox?: ICheckboxOption // 复选框信息。{width?:number; height?:number; gap?:number; lineWidth?:number; fillStyle?:string; strokeStyle?: string;}
|
||||||
|
radio?: IRadioOption // 单选框信息。{width?:number; height?:number; gap?:number; lineWidth?:number; fillStyle?:string; strokeStyle?: string;}
|
||||||
|
cursor?: ICursorOption // 光标样式。{width?: number; color?: string; dragWidth?: number; dragColor?: string;}
|
||||||
|
title?: ITitleOption // 标题配置。{ defaultFirstSize?: number; defaultSecondSize?: number; defaultThirdSize?: number defaultFourthSize?: number; defaultFifthSize?: number; defaultSixthSize?: number;}
|
||||||
|
placeholder?: IPlaceholder // 编辑器空白占位文本
|
||||||
|
group?: IGroup // 成组配置。{opacity?:number; backgroundColor?:string; activeOpacity?:number; activeBackgroundColor?:string; disabled?:boolean}
|
||||||
|
pageBreak?: IPageBreak // 分页符配置。{font?:string; fontSize?:number; lineDash?:number[];}
|
||||||
|
zone?: IZoneOption // 编辑器区域配置。{tipDisabled?:boolean;}
|
||||||
|
background?: IBackgroundOption // 背景配置。{color?:string; image?:string; size?:BackgroundSize; repeat?:BackgroundRepeat;}。默认:{color: '#FFFFFF'}
|
||||||
|
lineBreak?: ILineBreakOption // 换行符配置。{disabled?:boolean; color?:string; lineWidth?:number;}
|
||||||
|
separator?: ISeparatorOption // 分隔符配置。{lineWidth?:number; strokeStyle?:string;}
|
||||||
|
}
|
||||||
|
|
||||||
|
interface ITableOption {
|
||||||
|
tdPadding?: IPadding // 单元格内边距。默认:[0, 5, 5, 5]
|
||||||
|
defaultTrMinHeight?: number // 默认表格行最小高度。默认:42
|
||||||
|
defaultColMinWidth?: number // 默认表格列最小宽度(整体宽度足够时应用,否则会按比例缩小)。默认:40
|
||||||
|
}
|
||||||
|
|
||||||
|
interface IHeader {
|
||||||
|
top?: number // 距离页面顶部大小。默认:30
|
||||||
|
maxHeightRadio?: MaxHeightRatio // 占页面最大高度比。默认:HALF
|
||||||
|
disabled?: boolean // 是否禁用
|
||||||
|
}
|
||||||
|
|
||||||
|
interface IFooter {
|
||||||
|
bottom?: number // 距离页面底部大小。默认:30
|
||||||
|
maxHeightRadio?: MaxHeightRatio // 占页面最大高度比。默认:HALF
|
||||||
|
disabled?: boolean // 是否禁用
|
||||||
|
}
|
||||||
|
|
||||||
|
interface IPageNumber {
|
||||||
|
bottom?: number // 距离页面底部大小。默认:60
|
||||||
|
size?: number // 字体大小。默认:12
|
||||||
|
font?: string // 字体。默认:Microsoft YaHei
|
||||||
|
color?: string // 字体颜色。默认:#000000
|
||||||
|
rowFlex?: RowFlex // 行对齐方式。默认:CENTER
|
||||||
|
format?: string // 页码格式。默认:{pageNo}。示例:第{pageNo}页/共{pageCount}页
|
||||||
|
numberType?: NumberType // 数字类型。默认:ARABIC
|
||||||
|
disabled?: boolean // 是否禁用
|
||||||
|
startPageNo?: number // 起始页码。默认:1
|
||||||
|
fromPageNo?: number // 从第几页开始出现页码。默认:0
|
||||||
|
maxPageNo?: number | null // 最大页码(从0开始)。默认:null
|
||||||
|
}
|
||||||
|
|
||||||
|
interface IWatermark {
|
||||||
|
data: string // 文本。
|
||||||
|
color?: string // 颜色。默认:#AEB5C0
|
||||||
|
opacity?: number // 透明度。默认:0.3
|
||||||
|
size?: number // 字体大小。默认:200
|
||||||
|
font?: string // 字体。默认:Microsoft YaHei
|
||||||
|
}
|
||||||
|
|
||||||
|
interface IPlaceholder {
|
||||||
|
data: string // 文本。
|
||||||
|
color?: string // 颜色。默认:#DCDFE6
|
||||||
|
opacity?: number // 透明度。默认:1
|
||||||
|
size?: number // 字体大小。默认:16
|
||||||
|
font?: string // 字体。默认:Microsoft YaHei
|
||||||
|
}
|
30
vite.config.js
Normal file
|
@ -0,0 +1,30 @@
|
||||||
|
import { fileURLToPath, URL } from 'node:url'
|
||||||
|
|
||||||
|
import { defineConfig } from 'vite'
|
||||||
|
import vue from '@vitejs/plugin-vue'
|
||||||
|
|
||||||
|
// https://vitejs.dev/config/
|
||||||
|
export default defineConfig({
|
||||||
|
plugins: [
|
||||||
|
vue(),
|
||||||
|
],
|
||||||
|
resolve: {
|
||||||
|
alias: {
|
||||||
|
'@': fileURLToPath(new URL('./src', import.meta.url))
|
||||||
|
}
|
||||||
|
},
|
||||||
|
server: {
|
||||||
|
proxy: {
|
||||||
|
// 在此处编写代理规则
|
||||||
|
'/api': {
|
||||||
|
secure: false,
|
||||||
|
//target: 'https://192.168.3.198',
|
||||||
|
target: 'https://c.apxly.com',
|
||||||
|
changeOrigin: true,
|
||||||
|
rewrite: (path) => {
|
||||||
|
return path.replace(/\/api/, '')
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
})
|