├── .env.development ├── .env.production ├── .github └── workflows │ └── static.yml ├── .gitignore ├── .vscode └── extensions.json ├── ChangeLog.md ├── LICENSE ├── README.md ├── dist ├── assets │ ├── Emoji-94e48894.css │ ├── Emoji-fa6a078a.js │ ├── WtContent-b07e06d8.js │ ├── WtContent-dfe3f8f9.css │ ├── emojiBase64-09fa9685.js │ ├── index-50feddeb.js │ ├── index-689661ea.css │ ├── sf-pro-text_medium-921bf32d.woff2 │ ├── sf-pro-text_regular-1ef469b1.woff2 │ ├── sf-pro-text_semibold-80533297.woff2 │ ├── wechat-audio-light-59b09d30.png │ ├── wechat-bottom-icon1-dark-4ebaba34.png │ ├── wechat-bottom-icon4-light-f1d1afeb.png │ ├── wechat-trans-icon1-649f3379.png │ └── wechat-trans-icon2-f5f2e254.png ├── favicon.ico ├── gif.worker.js └── index.html ├── index.html ├── package-lock.json ├── package.json ├── public ├── favicon.ico └── gif.worker.js ├── snapshot ├── 01.jpg ├── 02.jpg ├── 1651905141755.jpg ├── 1651905463193.jpg ├── 1695047989076.gif ├── 1695049426372.gif ├── 1695050793373.gif └── 1695052489383.gif ├── src ├── App.vue ├── assets │ ├── fonts │ │ ├── sf-pro-text_medium.woff2 │ │ ├── sf-pro-text_regular.woff2 │ │ └── sf-pro-text_semibold.woff2 │ └── images │ │ ├── bar │ │ ├── ios-battery-charge-dark.png │ │ ├── ios-battery-charge-light.png │ │ ├── ios-battery-dark.png │ │ ├── ios-battery-light.png │ │ ├── ios-single-1-dark.png │ │ ├── ios-single-1-light.png │ │ ├── ios-single-2-dark.png │ │ ├── ios-single-2-light.png │ │ ├── ios-single-3-dark.png │ │ ├── ios-single-3-light.png │ │ ├── ios-single-4-dark.png │ │ ├── ios-single-4-light.png │ │ ├── ios-wifi-1-dark.png │ │ ├── ios-wifi-1-light.png │ │ ├── ios-wifi-2-dark.png │ │ ├── ios-wifi-2-light.png │ │ ├── ios-wifi-3-dark.png │ │ └── ios-wifi-3-light.png │ │ ├── bottom │ │ ├── phone-bottom-bar-dark.png │ │ ├── phone-bottom-bar-light.png │ │ ├── wechat-bottom-icon1-dark.png │ │ ├── wechat-bottom-icon1-light.png │ │ ├── wechat-bottom-icon2-dark.png │ │ ├── wechat-bottom-icon2-light.png │ │ ├── wechat-bottom-icon3-dark.png │ │ ├── wechat-bottom-icon3-light.png │ │ ├── wechat-bottom-icon4-dark.png │ │ └── wechat-bottom-icon4-light.png │ │ ├── content │ │ ├── wechat-audio-dark.png │ │ ├── wechat-audio-light.png │ │ ├── wechat-redp-icon1.png │ │ ├── wechat-trans-icon1.png │ │ ├── wechat-trans-icon2.png │ │ ├── wechat-trans-icon3.png │ │ ├── wechat-trans-icon4.png │ │ ├── wechat-video-dark.png │ │ ├── wechat-video-light.png │ │ ├── wechat-voice-icon1-dark.png │ │ ├── wechat-voice-icon1-light.png │ │ ├── wechat-voice-icon2-dark.png │ │ └── wechat-voice-icon2-light.png │ │ └── nav │ │ ├── wechat-nav-back-dark.png │ │ ├── wechat-nav-back-light.png │ │ ├── wechat-nav-right-dark.png │ │ ├── wechat-nav-right-light.png │ │ ├── wechat-trans-earphone-dark.png │ │ └── wechat-trans-earphone-light.png ├── components │ ├── ConfigAppearance.vue │ ├── ConfigChat.vue │ ├── ConfigInstructions.vue │ ├── ConfigTemplate.vue │ ├── WtContent.vue │ ├── WtHeader.vue │ ├── WtSider.vue │ ├── common │ │ ├── ContextMenu.vue │ │ ├── CustomUpload.vue │ │ ├── Disclaimers.vue │ │ ├── Emoji.vue │ │ ├── GenerateForm.vue │ │ ├── ImageEditor.vue │ │ ├── Instructions.vue │ │ ├── IsPhone.vue │ │ ├── Tutorial.vue │ │ └── UserManage.vue │ └── phone │ │ ├── PhoneBar.vue │ │ ├── PhoneBody.vue │ │ ├── PhoneBottom.vue │ │ ├── PhoneGenerate.vue │ │ ├── PhoneNav.vue │ │ ├── PhoneTools.vue │ │ └── generate │ │ ├── GeneConfig.vue │ │ ├── GeneGif.vue │ │ ├── GenePng.vue │ │ ├── GeneTemplate.vue │ │ └── GeneVideo.vue ├── global.less ├── hooks │ ├── useAutoScrollBottom.js │ └── useHtmlToImage.js ├── main.js ├── store │ ├── index.js │ ├── modules │ │ ├── chat.js │ │ ├── contextMenu.js │ │ ├── system.js │ │ ├── template.js │ │ └── user.js │ └── pinia.js └── utils │ ├── avatar.js │ ├── emojiBase64.js │ ├── enum.js │ ├── eventBus.js │ ├── feedback.js │ └── utils.js ├── vite.config.js └── yarn.lock /.env.development: -------------------------------------------------------------------------------- 1 | VITE_APP_ENV = development 2 | VITE_BASE_PATH = / -------------------------------------------------------------------------------- /.env.production: -------------------------------------------------------------------------------- 1 | VITE_APP_ENV = production 2 | VITE_BASE_PATH = /vue3-wechat-tool 3 | -------------------------------------------------------------------------------- /.github/workflows/static.yml: -------------------------------------------------------------------------------- 1 | # Simple workflow for deploying static content to GitHub Pages 2 | name: Deploy static content to Pages 3 | 4 | on: 5 | # Runs on pushes targeting the default branch 6 | push: 7 | branches: ["master"] 8 | 9 | # Allows you to run this workflow manually from the Actions tab 10 | workflow_dispatch: 11 | 12 | # Sets permissions of the GITHUB_TOKEN to allow deployment to GitHub Pages 13 | permissions: 14 | contents: read 15 | pages: write 16 | id-token: write 17 | 18 | # Allow only one concurrent deployment, skipping runs queued between the run in-progress and latest queued. 19 | # However, do NOT cancel in-progress runs as we want to allow these production deployments to complete. 20 | concurrency: 21 | group: "pages" 22 | cancel-in-progress: false 23 | 24 | jobs: 25 | # Single deploy job since we're just deploying 26 | deploy: 27 | environment: 28 | name: github-pages 29 | url: ${{ steps.deployment.outputs.page_url }} 30 | runs-on: ubuntu-latest 31 | steps: 32 | - name: Checkout 33 | uses: actions/checkout@v4 34 | - name: Setup Pages 35 | uses: actions/configure-pages@v5 36 | - name: Upload artifact 37 | uses: actions/upload-pages-artifact@v3 38 | with: 39 | # Upload entire repository 40 | path: './dist' 41 | - name: Deploy to GitHub Pages 42 | id: deployment 43 | uses: actions/deploy-pages@v4 44 | -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | # Logs 2 | logs 3 | *.log 4 | npm-debug.log* 5 | yarn-debug.log* 6 | yarn-error.log* 7 | pnpm-debug.log* 8 | lerna-debug.log* 9 | 10 | node_modules 11 | dist-ssr 12 | *.local 13 | 14 | # Editor directories and files 15 | .vscode/* 16 | !.vscode/extensions.json 17 | .idea 18 | .DS_Store 19 | *.suo 20 | *.ntvs* 21 | *.njsproj 22 | *.sln 23 | *.sw? 24 | -------------------------------------------------------------------------------- /.vscode/extensions.json: -------------------------------------------------------------------------------- 1 | { 2 | "recommendations": ["Vue.volar", "Vue.vscode-typescript-vue-plugin"] 3 | } 4 | -------------------------------------------------------------------------------- /ChangeLog.md: -------------------------------------------------------------------------------- 1 | # 更新日志 2 | 3 | - 🚀有好的想法或在使用中遇到问题,请提[issues](https://github.com/Ele-Cat/vue3-wechat-tool/issues/new) 4 | 5 | **2024-07-08** 6 | - 🌟新增群聊功能 7 | 8 | **2024-04-06** 9 | - 🌟新增发送系统消息功能,消息被拒收自动展示“消息已发出,但被对方拒收了。” 10 | - 🐞修复对话设置发送校验问题 11 | 12 | **2024-01-11** 13 | - 🐞修复生成长图时无背景问题 14 | 15 | **2023-09-25** 16 | - 🌟新增发送名片功能 17 | 18 | **2023-09-21** 19 | - 🌟新增生成视频功能【实际为生成图片序列自行剪辑】 20 | 21 | **2023-09-20** 22 | - 🌟新增导入导出聊天功能 23 | - 👌重构生成功能 24 | 25 | **2023-09-19** 26 | - 🌟新增生成动图功能 27 | - 🌟新增生成动图、视频配置【思考时间】 28 | 29 | **2023-09-18** 30 | - 🌟新增使用视频教程 31 | - 🌟新增模板管理标题修改功能 32 | 33 | **2023-09-18** 34 | - 🌟新增对话修改功能【右键菜单】 35 | - 🌟新增工具使用教程使用教程 36 | - 🐞修复一系列系统遗留问题 37 | 38 | **2023-09-17** 39 | - 🌟新增发送音频、视频邀请功能 40 | - 🌟新增拍一拍、撤回消息、消息被拒收功能 41 | - 🐞修复保存长图时背景图问题 42 | 43 | **2023-09-16** 44 | - 🌟新增深色模式 45 | - 🌟新增语音条转文字功能 46 | 47 | **2023-09-15** 48 | - 🌟新增模板预览功能 49 | 50 | **2023-09-14** 51 | - 🌟新增图片上传裁剪组件 `vue-advanced-cropper` 52 | - 🌟新增用户输入文本同步展示在聊天输入框功能 53 | - 🌟新增保存、应用模板功能 54 | 55 | **2023-09-13** 56 | - 🌟新增领取红包、转账功能【右键菜单】 57 | - 🐞修复保存长图最小高度问题 58 | 59 | **2023-09-12** 60 | - 🌟新增保存图片、长图功能 `html2canvas` 61 | 62 | **2023-09-11** 63 | - 🌟新增移动端打开提示去web端 64 | - 🐞调整手机组件、表情包组件为异步,加快首屏渲染速度 65 | 66 | **2023-09-10** 67 | - 🌟新增发送语音条功能 68 | - 🐞调整一系列样式问题 69 | 70 | **2023-09-09** 71 | - 🌟新增聊天工具【重置外观、清空聊天】 72 | - 🌟新增聊天条目上移、下移、移除功能【右键菜单】 73 | - 🌟新增上传聊天图片、转账、红包功能 74 | - 🐞修复聊天发送表情功能 75 | 76 | **2023-09-08** 77 | - 🌟完成项目聊天与用户解耦 78 | 79 | **2023-09-07** 80 | - 🌟新增手机外观设置联动 81 | - 🌟新增用户管理功能 82 | - 🐞优化界面滚动条样式 `vue3-perfect-scrollbar` 83 | 84 | **2023-09-06** 85 | - 🌟新增文本+表情包发送 86 | - 🌟完成项目数据持久化 `pinia`、`pinia-plugin-persist` 87 | - 🌟完成项目组件结构抽离 88 | - 🌟新增使用说明 89 | - 🌟新增免责声明 90 | - 🐞修复线上图片引用问题 91 | 92 | **2023-09-05** 93 | - 🌟项目立项 94 | - 🌟完成项目基础结构 95 | - 🌟完成基础外观设置 -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | MIT License 2 | 3 | Copyright (c) 2023 ele-cat 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy 6 | of this software and associated documentation files (the "Software"), to deal 7 | in the Software without restriction, including without limitation the rights 8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 | copies of the Software, and to permit persons to whom the Software is 10 | furnished to do so, subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in all 13 | copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 21 | SOFTWARE. 22 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 |

在线微信对话生成器 👋

2 | 3 | > 使用 Vite + Vue3 + AntDesignVue + Pinia 搭建的在线微信对话生成器 4 | 5 |
6 |

本程序是一款微信聊天记录制作工具,可以模拟微信聊天、管理不同用户角色进行对话,同时支持发送文字、图片、语音、红包、转账等类型信息。可以将聊天内容一键生成为图片、长图、动图和视频。【在线使用地址

7 |

全量开源,更多好玩的功能欢迎提出Issues,敬请期待!

8 |
9 | 10 |
11 | star 12 | fork 13 |
14 | 15 | ### 👉使用教程【视频】 16 | 17 | ### 👉使用教程【文本】 18 | 19 | ### 👉开发教程 20 | 21 | ### ✨在线使用 22 | 23 | ## 截图预览 24 | 25 | 26 | 27 | 28 | ![外观设置效果预览](./snapshot/1695047989076.gif) 29 | ![发送对话](./snapshot/1695050793373.gif) 30 | ![右键菜单](./snapshot/1695052489383.gif) 31 | 32 | 33 | ## 功能清单 34 | 35 |
36 | 点击展开 37 | 38 | - 界面结构 39 | - 外观设置 40 | - 基础外观设置 41 | - 上传图片裁剪 42 | - 深色模式 43 | - 机型切换 44 | - 对话设置 45 | - 用户管理 46 | - 消息发送 47 | - 发送文本、表情 48 | - 发送图片 49 | - 发送转账 50 | - 发送红包 51 | - 发送语音条 52 | - 语音条转文字 53 | - 时间 54 | - 发送视频、音频聊天 55 | - 发送名片 56 | - 拍一拍 57 | - 撤回消息 58 | - 消息被拒收 59 | - 手机聊天输入框同步展示文本 60 | - 对话内容操作【右键菜单】 61 | - 对话上移、下移 62 | - 对话移除 63 | - 对话领取红包、转账 64 | - 对话修改 65 | - 对话播放延时【生成动图、视频时,自定义距上条对话内容播放的延时时间】 66 | - 小工具 67 | - 重置外观 68 | - 清空对话 69 | - 生成操作 70 | - 存为模板 71 | - 生成图片 72 | - 生成长图 73 | - 生成动图、视频配置 74 | - 生成动图 75 | - 生成视频【实际为生成图片序列自行剪辑】 76 | - 聊天内容导入导出 77 | - **群聊** 78 | - 模板管理 79 | - 对话内容保存为模板 80 | - 应用模板 81 | - 预览模板 82 | - 删除模板 83 | - 使用说明 84 |
85 | 86 | ## 使用 87 | 88 | - #### 安装 89 | 90 | ``` 91 | npm install 92 | ``` 93 | 94 | - #### 运行 95 | 96 | ``` 97 | npm run serve 98 | ``` 99 | 100 | - #### 打包 101 | 102 | 打包前请注意将`.env.production`的`VITE_BASE_PATH`修改为`/` 103 | 104 | ``` 105 | npm run build 106 | ``` 107 | 108 | ## [更新日志](./ChangeLog.md) 109 | 110 | ## 支持 111 | 112 | 如果这个项目对你有帮助请给一个 ⭐️ 予以鼓励! 113 | 114 | ## 捐赠 115 | 116 | 117 | 118 | 119 | 120 | 121 | 您的赞赏与支持,是我最大的动力 -------------------------------------------------------------------------------- /dist/assets/Emoji-94e48894.css: -------------------------------------------------------------------------------- 1 | .emoji_wrap[data-v-7733f39f]{display:flex;flex-wrap:wrap;padding-left:8px}.emoji_wrap a[data-v-7733f39f]{display:block;width:24px;height:24px;margin:4px 5px}.emoji_wrap a img[data-v-7733f39f]{width:100%;height:100%}.emoji_wrap a p[data-v-7733f39f]{text-indent:-9999px;color:red} 2 | -------------------------------------------------------------------------------- /dist/assets/Emoji-fa6a078a.js: -------------------------------------------------------------------------------- 1 | import{_ as i,o as t,c as s,F as l,l as p,a as o,m as n,t as m,Q as d}from"./index-50feddeb.js";import{e as u}from"./emojiBase64-09fa9685.js";const f={class:"emoji_wrap",style:{"margin-top":"10px"}},g=["title","onClick"],k=["src"],h={__name:"Emoji",setup(v,{emit:_}){const c=a=>{_("add",a)};return(a,x)=>(t(),s("div",f,[(t(!0),s(l,null,p(n(d),(e,r)=>(t(),s("a",{key:r,title:e,onClick:y=>c(e)},[o("img",{src:"data:image/png;base64,"+n(u)[e],alt:""},null,8,k),o("p",null,m(e),1)],8,g))),128))]))}},B=i(h,[["__scopeId","data-v-7733f39f"]]);export{B as default}; 2 | -------------------------------------------------------------------------------- /dist/assets/index-689661ea.css: -------------------------------------------------------------------------------- 1 | @import"//at.alicdn.com/t/c/font_4238507_is5sbfgeqfc.css";.wt-header[data-v-142952fa]{position:relative;width:100%;height:100%;background-image:radial-gradient(ellipse farthest-side at 40% 0%,#1a2327 0%,#263238 60%,#455a64 100%);display:flex}.wt-header p[data-v-142952fa]{position:relative;margin:auto;font-size:32px;letter-spacing:.2em;display:inline-block;font-weight:700;white-space:nowrap;color:transparent;background-color:var(--theme-color);background-clip:text;-webkit-background-clip:text}.wt-header p[data-v-142952fa]:after{content:attr(data-text);position:absolute;left:0;top:0;width:100%;height:100%;z-index:5;background-image:linear-gradient(120deg,transparent 0%,transparent 6rem,white 11rem,transparent 11.15rem,transparent 15rem,rgba(255,255,255,.3) 20rem,transparent 25rem,transparent 27rem,rgba(255,255,255,.6) 32rem,white 33rem,rgba(255,255,255,.3) 33.15rem,transparent 38rem,transparent 40rem,rgba(255,255,255,.3) 45rem,transparent 50rem,transparent 100%);background-clip:text;-webkit-background-clip:text;background-size:150% 100%;background-repeat:no-repeat;animation:shine-142952fa 8s infinite linear}.wt-header img[data-v-142952fa]{position:absolute;left:calc(50% + 144px);bottom:6px}@keyframes shine-142952fa{0%{background-position:290% 0}to{background-position:-290% 0}}.vue-advanced-cropper{text-align:center;position:relative;-webkit-user-select:none;user-select:none;max-height:100%;max-width:100%;direction:ltr}.vue-advanced-cropper__stretcher{pointer-events:none;position:relative;max-width:100%;max-height:100%}.vue-advanced-cropper__image{-webkit-user-select:none;user-select:none;position:absolute;transform-origin:center;max-width:none!important}.vue-advanced-cropper__background,.vue-advanced-cropper__foreground{opacity:1;background:black;transform:translate(-50%,-50%);position:absolute;top:50%;left:50%}.vue-advanced-cropper__foreground{opacity:.5}.vue-advanced-cropper__boundaries{opacity:1;transform:translate(-50%,-50%);position:absolute;left:50%;top:50%}.vue-advanced-cropper__cropper-wrapper{width:100%;height:100%}.vue-advanced-cropper__image-wrapper{overflow:hidden;position:absolute;width:100%;height:100%}.vue-advanced-cropper__stencil-wrapper{position:absolute}.vue-handler-wrapper{position:absolute;transform:translate(-50%,-50%);width:30px;height:30px}.vue-handler-wrapper__draggable{width:100%;height:100%;display:flex;align-items:center;justify-content:center}.vue-handler-wrapper--west-north{cursor:nw-resize}.vue-handler-wrapper--north{cursor:n-resize}.vue-handler-wrapper--east-north{cursor:ne-resize}.vue-handler-wrapper--east{cursor:e-resize}.vue-handler-wrapper--east-south{cursor:se-resize}.vue-handler-wrapper--south{cursor:s-resize}.vue-handler-wrapper--west-south{cursor:sw-resize}.vue-handler-wrapper--west{cursor:w-resize}.vue-handler-wrapper--disabled{cursor:auto}.vue-line-wrapper{background:none;position:absolute;display:flex;align-items:center;justify-content:center}.vue-line-wrapper--north,.vue-line-wrapper--south{height:12px;width:100%;left:0;transform:translateY(-50%)}.vue-line-wrapper--north{top:0;cursor:n-resize}.vue-line-wrapper--south{top:100%;cursor:s-resize}.vue-line-wrapper--east,.vue-line-wrapper--west{width:12px;height:100%;transform:translate(-50%);top:0}.vue-line-wrapper--east{left:100%;cursor:e-resize}.vue-line-wrapper--west{left:0;cursor:w-resize}.vue-line-wrapper--disabled{cursor:auto}.vue-bounding-box{position:relative;height:100%;width:100%}.vue-bounding-box__handler{position:absolute}.vue-bounding-box__handler--west-north{left:0;top:0}.vue-bounding-box__handler--north{left:50%;top:0}.vue-bounding-box__handler--east-north{left:100%;top:0}.vue-bounding-box__handler--east{left:100%;top:50%}.vue-bounding-box__handler--east-south{left:100%;top:100%}.vue-bounding-box__handler--south{left:50%;top:100%}.vue-bounding-box__handler--west-south{left:0;top:100%}.vue-bounding-box__handler--west{left:0;top:50%}.vue-draggable-area{position:relative}.vue-preview-result{overflow:hidden;box-sizing:border-box;position:absolute;height:100%;width:100%}.vue-preview-result__wrapper{position:absolute}.vue-preview-result__image{pointer-events:none;position:relative;-webkit-user-select:none;user-select:none;transform-origin:center;max-width:none!important}.vue-simple-handler{display:block;background:white;height:10px;width:10px}.vue-simple-line{background:none;transition:border .5s;border-color:#ffffff4d;border-width:0;border-style:solid}.vue-simple-line--south,.vue-simple-line--north{height:0;width:100%}.vue-simple-line--east,.vue-simple-line--west{height:100%;width:0}.vue-simple-line--east{border-right-width:1px}.vue-simple-line--west{border-left-width:1px}.vue-simple-line--south{border-bottom-width:1px}.vue-simple-line--north{border-top-width:1px}.vue-simple-line--hover{opacity:1;border-color:#fff}.vue-preview{overflow:hidden;box-sizing:border-box;position:relative}.vue-preview--fill{width:100%;height:100%;position:absolute}.vue-preview__wrapper{position:absolute;height:100%;width:100%}.vue-preview__image{pointer-events:none;position:absolute;-webkit-user-select:none;user-select:none;transform-origin:center;max-width:none!important}.vue-rectangle-stencil{position:absolute;height:100%;width:100%;box-sizing:border-box}.vue-rectangle-stencil__preview{position:absolute;width:100%;height:100%}.vue-rectangle-stencil--movable{cursor:move}.vue-circle-stencil{position:absolute;height:100%;width:100%;box-sizing:content-box;cursor:move}.vue-circle-stencil__preview{border-radius:50%;position:absolute;width:100%;height:100%}.vue-circle-stencil--movable{cursor:move}.vue-simple-line{border-color:#fffc}.vue-simple-handler{display:block;position:relative;-ms-flex-negative:0;flex-shrink:0;-webkit-transition:opacity .5s;transition:opacity .5s;border:none;background:white;height:8px;width:8px;opacity:.5}.vue-simple-handler--hover{opacity:1}.vue-circle-stencil__preview{border:solid 2px rgba(255,255,255,.8)}.vue-circle-stencil .vue-simple-line{border-color:#ffffff4d}.vue-circle-stencil .vue-simple-handler--west-north,.vue-circle-stencil .vue-simple-handler--east-south,.vue-circle-stencil .vue-simple-handler--west-south,.vue-circle-stencil .vue-simple-handler--east-north{opacity:.5}.vue-circle-stencil .vue-simple-handler--hover{opacity:1}.vue-circle-stencil__preview:after,.vue-circle-stencil__preview:before,.vue-rectangle-stencil__preview:after,.vue-rectangle-stencil__preview:before{content:"";opacity:0;-webkit-transition:opacity .25s;transition:opacity .25s;position:absolute;pointer-events:none;z-index:1}.vue-circle-stencil__preview:after,.vue-rectangle-stencil__preview:after{border-left:dashed 1px white;border-right:dashed 1px white;width:33%;height:100%;-webkit-transform:translateX(-50%);transform:translate(-50%);left:50%;top:0}.vue-circle-stencil__preview:before,.vue-rectangle-stencil__preview:before{border-top:dashed 1px white;border-bottom:dashed 1px white;height:33%;width:100%;-webkit-transform:translateY(-50%);transform:translateY(-50%);top:50%;left:0}.vue-circle-stencil--moving .vue-rectangle-stencil__preview:after,.vue-circle-stencil--moving .vue-rectangle-stencil__preview:before,.vue-circle-stencil--moving .vue-circle-stencil__preview:after,.vue-circle-stencil--moving .vue-circle-stencil__preview:before,.vue-circle-stencil--resizing .vue-rectangle-stencil__preview:after,.vue-circle-stencil--resizing .vue-rectangle-stencil__preview:before,.vue-circle-stencil--resizing .vue-circle-stencil__preview:after,.vue-circle-stencil--resizing .vue-circle-stencil__preview:before,.vue-rectangle-stencil--moving .vue-rectangle-stencil__preview:after,.vue-rectangle-stencil--moving .vue-rectangle-stencil__preview:before,.vue-rectangle-stencil--moving .vue-circle-stencil__preview:after,.vue-rectangle-stencil--moving .vue-circle-stencil__preview:before,.vue-rectangle-stencil--resizing .vue-rectangle-stencil__preview:after,.vue-rectangle-stencil--resizing .vue-rectangle-stencil__preview:before,.vue-rectangle-stencil--resizing .vue-circle-stencil__preview:after,.vue-rectangle-stencil--resizing .vue-circle-stencil__preview:before{opacity:.7}.vue-circle-stencil--moving .vue-simple-handler,.vue-circle-stencil--resizing .vue-simple-handler,.vue-rectangle-stencil--moving .vue-simple-handler,.vue-rectangle-stencil--resizing .vue-simple-handler{opacity:1}.upload-box[data-v-a6f9c119]{display:flex;justify-content:center;align-items:center;background-color:#00000005;border:1px dashed #d9d9d9;border-radius:8px;cursor:pointer;transition:border-color .3s;color:#666;font-size:14px}.upload-box[data-v-a6f9c119]:hover{border-color:#fd6585}.upload-box .img-remove[data-v-a6f9c119]{position:absolute;left:90px;top:-8px;border-radius:50%;background-color:#fff;font-size:22px;color:#f05f57}.upload-box .img-remove[data-v-a6f9c119]:hover{color:red}.upload-box .img-show[data-v-a6f9c119]{width:100%;height:100%;object-fit:cover}.upload-box .img-upload[data-v-a6f9c119]{display:flex;flex-direction:column;justify-content:center;align-items:center}.upload-box .img-upload span[data-v-a6f9c119]{font-size:18px;margin-top:12px}.upload-box .img-upload p[data-v-a6f9c119]{margin-top:6px}.vue-advanced-cropper__background[data-v-a6f9c119],.vue-advanced-cropper__foreground[data-v-a6f9c119]{background-color:#f0f0f0}.cropper[data-v-a6f9c119]{height:600px;background:#eee}.config-appearance[data-v-63fa4831]{overflow-x:hidden}.config-appearance .phone-time[data-v-63fa4831]{display:flex;justify-content:space-between;align-items:center}.config-appearance .phone-time .ant-select[data-v-63fa4831]{width:38%}.config-appearance .ant-input-number[data-v-63fa4831]{width:100%}.config-appearance .avatar-uploader .ant-upload[data-v-63fa4831]{width:128px;height:128px}.config-appearance .avatar-uploader .ant-upload-select-picture-card i[data-v-63fa4831]{font-size:32px;color:#999}.config-appearance .avatar-uploader .ant-upload-select-picture-card .ant-upload-image[data-v-63fa4831]{width:100%;height:100%;object-fit:cover}.config-appearance .avatar-uploader .ant-upload-select-picture-card .img-remove[data-v-63fa4831]{position:absolute;left:90px;top:-8px;border-radius:50%;background-color:#fff;font-size:22px;color:#f05f57}.config-appearance .avatar-uploader .ant-upload-select-picture-card .img-remove[data-v-63fa4831]:hover{color:red}.config-appearance .avatar-uploader .ant-upload-select-picture-card .ant-upload-text[data-v-63fa4831]{margin-top:8px;color:#666}.generate-form .emojis[data-v-792ae918]{display:flex;flex-wrap:wrap;background-color:#f9f9f9;max-height:136px;overflow-y:auto}.generate-form .emojis img[data-v-792ae918]{width:22px;margin:4px 5px}.generate-form .ant-upload-dragger-image[data-v-792ae918]{max-width:100%;max-height:360px}.generate-form .datetime-select[data-v-792ae918]{display:flex;align-items:center;margin-bottom:6px}.generate-form .datetime-select .ant-select[data-v-792ae918]{width:90px;margin-right:4px}.generate-form .datetime-select .ant-select[data-v-792ae918]:not(.generate-form .datetime-select .ant-select:nth-of-type(1)){margin-left:10px}.generate-form .time-preview[data-v-792ae918]{display:inline-block;font-size:18px;color:var(--theme-color);margin-top:12px}.generate-form .ant-card-body{padding-top:12px}.generate-form .ant-upload-drag-hover{background-color:#90f7ec}.generate-form .ant-input-number{width:100%}.config-label[data-v-64628faa]{display:flex;justify-content:space-between;align-items:center}.user-select-box[data-v-64628faa]{display:flex;align-items:center;flex-wrap:wrap;background-color:#f5f5f5;border-radius:4px;padding:16px 0 6px 10px;margin-top:6px}.user-select-box .user-item[data-v-64628faa]{position:relative;width:88px;height:88px;display:flex;flex-direction:column;justify-content:space-between;align-items:center;border-radius:4px;cursor:pointer;margin:0 10px 10px 0}.user-select-box .user-item.active[data-v-64628faa]{background-color:#fff;color:var(--theme-color)}.user-select-box .user-item .ant-input[data-v-64628faa]{text-align:center}.user-select-box .user-item p[data-v-64628faa]{margin:2px 0 0;max-width:80%;font-size:14px;overflow:hidden;text-overflow:ellipsis;white-space:nowrap}.user-select-box .user-item .user-select[data-v-64628faa]{position:absolute;right:0;bottom:22px}.user-select-box .user-item .user-delete[data-v-64628faa]{position:absolute;right:6px;top:-6px;background-color:red;color:#fff;z-index:999;font-size:12px;width:18px;height:18px;display:flex;align-items:center;justify-content:center;border-radius:50%}.user-select-box .add-btn[data-v-64628faa]{width:88px;height:88px;border:1px dashed #ccc;display:flex;justify-content:center;align-items:center;font-size:24px;color:#ccc;cursor:pointer;transition:all .3s}.user-select-box .add-btn[data-v-64628faa]:hover{color:var(--theme-color);border:1px dashed var(--theme-color)}.avatar-uploader>.ant-upload[data-v-64628faa]{width:128px;height:128px}.ant-upload-select-picture-card i[data-v-64628faa]{font-size:32px;color:#999}.ant-upload-select-picture-card .ant-upload-text[data-v-64628faa]{margin-top:-12px;font-size:46px;color:#666}.config-chat .ant-tabs .ant-tabs-tab+.ant-tabs-tab{margin:0 0 0 10px}.template-control[data-v-58b21333]{display:flex;justify-content:space-between;align-items:center;margin-bottom:10px;color:var(--theme-color)}.config-template .table-striped td{background-color:#fafafa!important}.disclaimers-drawer .indent[data-v-f2be6e9c]{padding-left:6px}.disclaimers-drawer p[data-v-f2be6e9c]{margin:0 0 4px;text-align:justify;line-height:1.4}.disclaimers-drawer p.bold[data-v-f2be6e9c]{font-weight:700}.disclaimers-root .ant-drawer-content-wrapper{max-width:500px}.config-instructions p[data-v-c2dcd184]{font-size:16px;line-height:1.4}.config-instructions a[data-v-c2dcd184]{text-decoration:underline}.config-instructions .text-orange[data-v-c2dcd184]{color:#fb923c}.config-instructions .disclaimers[data-v-c2dcd184]{text-decoration:underline;color:#fd6585;cursor:pointer}.config-instructions .disclaimers[data-v-c2dcd184]:hover{color:red}.wt-sider[data-v-8d2dbc8a]{display:flex;height:100%}.wt-sider .menu-box[data-v-8d2dbc8a]{width:80px;height:100%;background-color:#455a64}.wt-sider .menu-box .menu-item[data-v-8d2dbc8a]{display:flex;flex-direction:column;align-items:center;justify-content:center;height:80px;cursor:pointer;transition:all .3s;color:#ddd}.wt-sider .menu-box .menu-item i[data-v-8d2dbc8a]{font-size:24px;margin-bottom:6px}.wt-sider .menu-box .menu-item.active[data-v-8d2dbc8a]{background-color:#f9f9f9;color:var(--theme-color)}.wt-sider .menu-box .menu-item[data-v-8d2dbc8a]:hover{background-color:#f5f5f5;color:var(--theme-color)}.wt-sider .menu-box .menu-item p[data-v-8d2dbc8a]{margin:0}.wt-config[data-v-8d2dbc8a]{width:calc(100% - 80px);flex:1;padding:20px}.custom-menu[data-v-70661503]{position:fixed;top:0;left:0;background-color:#fff;box-sizing:border-box;box-shadow:0 0 8px #0003;border-radius:5px;z-index:99}.custom-menu>ul[data-v-70661503]{padding:0;margin:0;list-style:none;font-size:12px;color:#000;border:1px solid #C4C4C4}.custom-menu>ul li[data-v-70661503]{height:28px;line-height:28px;padding:0 20px}.custom-menu>ul li.red[data-v-70661503]{color:#ff4d4f}.custom-menu>ul li[data-v-70661503]:hover{background-color:#e2e2e2}.custom-menu>ul .border-top[data-v-70661503]{border-top:1px solid #EDEDED}.custom-menu.show[data-v-70661503]{display:block}.is-phone[data-v-ef9d2cf8]{height:100%;display:flex;flex-direction:column;justify-content:center;align-items:center;font-size:28px}.content[data-v-71a32bba]{height:calc(100vh - 50px);background-color:#fff;background-image:linear-gradient(90deg,rgba(159,219,252,.35) 3%,transparent 0),linear-gradient(1turn,rgba(159,219,252,.35) 3%,transparent 0);background-size:20px 20px;background-position:50%;background-attachment:fixed}.widget[data-v-71a32bba]{position:fixed;top:0;right:0}html,body{width:100%;height:100%}input::-ms-clear,input::-ms-reveal{display:none}*,*:before,*:after{box-sizing:border-box}html{font-family:sans-serif;line-height:1.15;-webkit-text-size-adjust:100%;-ms-text-size-adjust:100%;-ms-overflow-style:scrollbar;-webkit-tap-highlight-color:rgba(0,0,0,0)}@-ms-viewport{width:device-width}body{margin:0}[tabindex="-1"]:focus{outline:none}hr{box-sizing:content-box;height:0;overflow:visible}h1,h2,h3,h4,h5,h6{margin-top:0;margin-bottom:.5em;font-weight:500}p{margin-top:0;margin-bottom:1em}abbr[title],abbr[data-original-title]{-webkit-text-decoration:underline dotted;text-decoration:underline;text-decoration:underline dotted;border-bottom:0;cursor:help}address{margin-bottom:1em;font-style:normal;line-height:inherit}input[type=text],input[type=password],input[type=number],textarea{-webkit-appearance:none}ol,ul,dl{margin-top:0;margin-bottom:1em}ol ol,ul ul,ol ul,ul ol{margin-bottom:0}dt{font-weight:500}dd{margin-bottom:.5em;margin-left:0}blockquote{margin:0 0 1em}dfn{font-style:italic}b,strong{font-weight:bolder}small{font-size:80%}sub,sup{position:relative;font-size:75%;line-height:0;vertical-align:baseline}sub{bottom:-.25em}sup{top:-.5em}pre,code,kbd,samp{font-size:1em;font-family:SFMono-Regular,Consolas,Liberation Mono,Menlo,Courier,monospace}pre{margin-top:0;margin-bottom:1em;overflow:auto}figure{margin:0 0 1em}img{vertical-align:middle;border-style:none}a,area,button,[role=button],input:not([type=range]),label,select,summary,textarea{touch-action:manipulation}table{border-collapse:collapse}caption{padding-top:.75em;padding-bottom:.3em;text-align:left;caption-side:bottom}input,button,select,optgroup,textarea{margin:0;color:inherit;font-size:inherit;font-family:inherit;line-height:inherit}button,input{overflow:visible}button,select{text-transform:none}button,html [type=button],[type=reset],[type=submit]{-webkit-appearance:button}button::-moz-focus-inner,[type=button]::-moz-focus-inner,[type=reset]::-moz-focus-inner,[type=submit]::-moz-focus-inner{padding:0;border-style:none}input[type=radio],input[type=checkbox]{box-sizing:border-box;padding:0}input[type=date],input[type=time],input[type=datetime-local],input[type=month]{-webkit-appearance:listbox}textarea{overflow:auto;resize:vertical}fieldset{min-width:0;margin:0;padding:0;border:0}legend{display:block;width:100%;max-width:100%;margin-bottom:.5em;padding:0;color:inherit;font-size:1.5em;line-height:inherit;white-space:normal}progress{vertical-align:baseline}[type=number]::-webkit-inner-spin-button,[type=number]::-webkit-outer-spin-button{height:auto}[type=search]{outline-offset:-2px;-webkit-appearance:none}[type=search]::-webkit-search-cancel-button,[type=search]::-webkit-search-decoration{-webkit-appearance:none}::-webkit-file-upload-button{font:inherit;-webkit-appearance:button}output{display:inline-block}summary{display:list-item}template{display:none}[hidden]{display:none!important}mark{padding:.2em;background-color:#feffe6}:root{scroll-behavior:smooth;--theme-color: #FD6585;--light-bg-color: #EDEDED;--light-text-color: #1A1A1A;--dark-bg-color: #232323;--dark-text-color: snow}#app{-webkit-user-select:none;user-select:none;max-height:100vh;overflow:hidden}@font-face{font-family:SF Pro;font-style:normal;font-weight:600;src:url(/vue3-wechat-tool/assets/sf-pro-text_semibold-80533297.woff2) format("woff2")}@font-face{font-family:SF Pro;font-style:normal;font-weight:500;src:url(/vue3-wechat-tool/assets/sf-pro-text_medium-921bf32d.woff2) format("woff2")}@font-face{font-family:SF Pro;font-style:normal;font-weight:400;src:url(/vue3-wechat-tool/assets/sf-pro-text_regular-1ef469b1.woff2) format("woff2")}img{-webkit-user-drag:none;-webkit-user-select:none;-moz-user-select:none;-ms-user-select:none;user-select:none}::-webkit-scrollbar{width:8px;height:8px}::-webkit-scrollbar-thumb{border-radius:4px;box-shadow:inset 0 0 5px #cac8c6;background:#cac8c6}::-webkit-scrollbar-track{background:0 0;border-radius:1px}.ps{position:relative;height:100%;overflow-y:hidden}.ps .ps__rail-x:hover,.ps .ps__rail-y:hover,.ps .ps__rail-x:focus,.ps .ps__rail-y:focus,.ps .ps__rail-x.ps--clicking,.ps .ps__rail-y.ps--clicking{background-color:transparent!important}.ps__rail-y:hover>.ps__thumb-y,.ps__rail-y:focus>.ps__thumb-y,.ps__rail-y.ps--clicking .ps__thumb-y{width:8px!important}.ant-form-item{margin-bottom:14px}.default-loading{flex:1;height:136px;display:flex;flex-direction:column;justify-content:center;align-items:center}.form-tip{position:absolute;font-size:12px;color:gray}.ps{overflow:hidden!important;overflow-anchor:none;-ms-overflow-style:none;touch-action:auto;-ms-touch-action:auto}.ps__rail-x{display:none;opacity:0;transition:background-color .2s linear,opacity .2s linear;-webkit-transition:background-color .2s linear,opacity .2s linear;height:15px;bottom:0;position:absolute}.ps__rail-y{display:none;opacity:0;transition:background-color .2s linear,opacity .2s linear;-webkit-transition:background-color .2s linear,opacity .2s linear;width:15px;right:0;position:absolute}.ps--active-x>.ps__rail-x,.ps--active-y>.ps__rail-y{display:block;background-color:transparent}.ps:hover>.ps__rail-x,.ps:hover>.ps__rail-y,.ps--focus>.ps__rail-x,.ps--focus>.ps__rail-y,.ps--scrolling-x>.ps__rail-x,.ps--scrolling-y>.ps__rail-y{opacity:.6}.ps .ps__rail-x:hover,.ps .ps__rail-y:hover,.ps .ps__rail-x:focus,.ps .ps__rail-y:focus,.ps .ps__rail-x.ps--clicking,.ps .ps__rail-y.ps--clicking{background-color:#eee;opacity:.9}.ps__thumb-x{background-color:#aaa;border-radius:6px;transition:background-color .2s linear,height .2s ease-in-out;-webkit-transition:background-color .2s linear,height .2s ease-in-out;height:6px;bottom:2px;position:absolute}.ps__thumb-y{background-color:#aaa;border-radius:6px;transition:background-color .2s linear,width .2s ease-in-out;-webkit-transition:background-color .2s linear,width .2s ease-in-out;width:6px;right:2px;position:absolute}.ps__rail-x:hover>.ps__thumb-x,.ps__rail-x:focus>.ps__thumb-x,.ps__rail-x.ps--clicking .ps__thumb-x{background-color:#999;height:11px}.ps__rail-y:hover>.ps__thumb-y,.ps__rail-y:focus>.ps__thumb-y,.ps__rail-y.ps--clicking .ps__thumb-y{background-color:#999;width:11px}@supports (-ms-overflow-style: none){.ps{overflow:auto!important}}@media screen and (-ms-high-contrast: active),(-ms-high-contrast: none){.ps{overflow:auto!important}}.ps{position:relative} 2 | -------------------------------------------------------------------------------- /dist/assets/sf-pro-text_medium-921bf32d.woff2: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Ele-Cat/vue3-wechat-tool/3626955435e1c241df7f4f225d06a72756cc806c/dist/assets/sf-pro-text_medium-921bf32d.woff2 -------------------------------------------------------------------------------- /dist/assets/sf-pro-text_regular-1ef469b1.woff2: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Ele-Cat/vue3-wechat-tool/3626955435e1c241df7f4f225d06a72756cc806c/dist/assets/sf-pro-text_regular-1ef469b1.woff2 -------------------------------------------------------------------------------- /dist/assets/sf-pro-text_semibold-80533297.woff2: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Ele-Cat/vue3-wechat-tool/3626955435e1c241df7f4f225d06a72756cc806c/dist/assets/sf-pro-text_semibold-80533297.woff2 -------------------------------------------------------------------------------- /dist/assets/wechat-audio-light-59b09d30.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Ele-Cat/vue3-wechat-tool/3626955435e1c241df7f4f225d06a72756cc806c/dist/assets/wechat-audio-light-59b09d30.png -------------------------------------------------------------------------------- /dist/assets/wechat-bottom-icon1-dark-4ebaba34.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Ele-Cat/vue3-wechat-tool/3626955435e1c241df7f4f225d06a72756cc806c/dist/assets/wechat-bottom-icon1-dark-4ebaba34.png -------------------------------------------------------------------------------- /dist/assets/wechat-bottom-icon4-light-f1d1afeb.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Ele-Cat/vue3-wechat-tool/3626955435e1c241df7f4f225d06a72756cc806c/dist/assets/wechat-bottom-icon4-light-f1d1afeb.png -------------------------------------------------------------------------------- /dist/assets/wechat-trans-icon1-649f3379.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Ele-Cat/vue3-wechat-tool/3626955435e1c241df7f4f225d06a72756cc806c/dist/assets/wechat-trans-icon1-649f3379.png -------------------------------------------------------------------------------- /dist/assets/wechat-trans-icon2-f5f2e254.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Ele-Cat/vue3-wechat-tool/3626955435e1c241df7f4f225d06a72756cc806c/dist/assets/wechat-trans-icon2-f5f2e254.png -------------------------------------------------------------------------------- /dist/favicon.ico: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Ele-Cat/vue3-wechat-tool/3626955435e1c241df7f4f225d06a72756cc806c/dist/favicon.ico -------------------------------------------------------------------------------- /dist/gif.worker.js: -------------------------------------------------------------------------------- 1 | // gif.worker.js 0.2.0 - https://github.com/jnordberg/gif.js 2 | (function e(t,n,r){function s(o,u){if(!n[o]){if(!t[o]){var a=typeof require=="function"&&require;if(!u&&a)return a(o,!0);if(i)return i(o,!0);var f=new Error("Cannot find module '"+o+"'");throw f.code="MODULE_NOT_FOUND",f}var l=n[o]={exports:{}};t[o][0].call(l.exports,function(e){var n=t[o][1][e];return s(n?n:e)},l,l.exports,e,t,n,r)}return n[o].exports}var i=typeof require=="function"&&require;for(var o=0;o=ByteArray.pageSize)this.newPage();this.pages[this.page][this.cursor++]=val};ByteArray.prototype.writeUTFBytes=function(string){for(var l=string.length,i=0;i=0)this.dispose=disposalCode};GIFEncoder.prototype.setRepeat=function(repeat){this.repeat=repeat};GIFEncoder.prototype.setTransparent=function(color){this.transparent=color};GIFEncoder.prototype.addFrame=function(imageData){this.image=imageData;this.colorTab=this.globalPalette&&this.globalPalette.slice?this.globalPalette:null;this.getImagePixels();this.analyzePixels();if(this.globalPalette===true)this.globalPalette=this.colorTab;if(this.firstFrame){this.writeLSD();this.writePalette();if(this.repeat>=0){this.writeNetscapeExt()}}this.writeGraphicCtrlExt();this.writeImageDesc();if(!this.firstFrame&&!this.globalPalette)this.writePalette();this.writePixels();this.firstFrame=false};GIFEncoder.prototype.finish=function(){this.out.writeByte(59)};GIFEncoder.prototype.setQuality=function(quality){if(quality<1)quality=1;this.sample=quality};GIFEncoder.prototype.setDither=function(dither){if(dither===true)dither="FloydSteinberg";this.dither=dither};GIFEncoder.prototype.setGlobalPalette=function(palette){this.globalPalette=palette};GIFEncoder.prototype.getGlobalPalette=function(){return this.globalPalette&&this.globalPalette.slice&&this.globalPalette.slice(0)||this.globalPalette};GIFEncoder.prototype.writeHeader=function(){this.out.writeUTFBytes("GIF89a")};GIFEncoder.prototype.analyzePixels=function(){if(!this.colorTab){this.neuQuant=new NeuQuant(this.pixels,this.sample);this.neuQuant.buildColormap();this.colorTab=this.neuQuant.getColormap()}if(this.dither){this.ditherPixels(this.dither.replace("-serpentine",""),this.dither.match(/-serpentine/)!==null)}else{this.indexPixels()}this.pixels=null;this.colorDepth=8;this.palSize=7;if(this.transparent!==null){this.transIndex=this.findClosest(this.transparent,true)}};GIFEncoder.prototype.indexPixels=function(imgq){var nPix=this.pixels.length/3;this.indexedPixels=new Uint8Array(nPix);var k=0;for(var j=0;j=0&&x1+x=0&&y1+y>16,(c&65280)>>8,c&255,used)};GIFEncoder.prototype.findClosestRGB=function(r,g,b,used){if(this.colorTab===null)return-1;if(this.neuQuant&&!used){return this.neuQuant.lookupRGB(r,g,b)}var c=b|g<<8|r<<16;var minpos=0;var dmin=256*256*256;var len=this.colorTab.length;for(var i=0,index=0;i=0){disp=dispose&7}disp<<=2;this.out.writeByte(0|disp|0|transp);this.writeShort(this.delay);this.out.writeByte(this.transIndex);this.out.writeByte(0)};GIFEncoder.prototype.writeImageDesc=function(){this.out.writeByte(44);this.writeShort(0);this.writeShort(0);this.writeShort(this.width);this.writeShort(this.height);if(this.firstFrame||this.globalPalette){this.out.writeByte(0)}else{this.out.writeByte(128|0|0|0|this.palSize)}};GIFEncoder.prototype.writeLSD=function(){this.writeShort(this.width);this.writeShort(this.height);this.out.writeByte(128|112|0|this.palSize);this.out.writeByte(0);this.out.writeByte(0)};GIFEncoder.prototype.writeNetscapeExt=function(){this.out.writeByte(33);this.out.writeByte(255);this.out.writeByte(11);this.out.writeUTFBytes("NETSCAPE2.0");this.out.writeByte(3);this.out.writeByte(1);this.writeShort(this.repeat);this.out.writeByte(0)};GIFEncoder.prototype.writePalette=function(){this.out.writeBytes(this.colorTab);var n=3*256-this.colorTab.length;for(var i=0;i>8&255)};GIFEncoder.prototype.writePixels=function(){var enc=new LZWEncoder(this.width,this.height,this.indexedPixels,this.colorDepth);enc.encode(this.out)};GIFEncoder.prototype.stream=function(){return this.out};module.exports=GIFEncoder},{"./LZWEncoder.js":2,"./TypedNeuQuant.js":3}],2:[function(require,module,exports){var EOF=-1;var BITS=12;var HSIZE=5003;var masks=[0,1,3,7,15,31,63,127,255,511,1023,2047,4095,8191,16383,32767,65535];function LZWEncoder(width,height,pixels,colorDepth){var initCodeSize=Math.max(2,colorDepth);var accum=new Uint8Array(256);var htab=new Int32Array(HSIZE);var codetab=new Int32Array(HSIZE);var cur_accum,cur_bits=0;var a_count;var free_ent=0;var maxcode;var clear_flg=false;var g_init_bits,ClearCode,EOFCode;function char_out(c,outs){accum[a_count++]=c;if(a_count>=254)flush_char(outs)}function cl_block(outs){cl_hash(HSIZE);free_ent=ClearCode+2;clear_flg=true;output(ClearCode,outs)}function cl_hash(hsize){for(var i=0;i=0){disp=hsize_reg-i;if(i===0)disp=1;do{if((i-=disp)<0)i+=hsize_reg;if(htab[i]===fcode){ent=codetab[i];continue outer_loop}}while(htab[i]>=0)}output(ent,outs);ent=c;if(free_ent<1<0){outs.writeByte(a_count);outs.writeBytes(accum,0,a_count);a_count=0}}function MAXCODE(n_bits){return(1<0)cur_accum|=code<=8){char_out(cur_accum&255,outs);cur_accum>>=8;cur_bits-=8}if(free_ent>maxcode||clear_flg){if(clear_flg){maxcode=MAXCODE(n_bits=g_init_bits);clear_flg=false}else{++n_bits;if(n_bits==BITS)maxcode=1<0){char_out(cur_accum&255,outs);cur_accum>>=8;cur_bits-=8}flush_char(outs)}}this.encode=encode}module.exports=LZWEncoder},{}],3:[function(require,module,exports){var ncycles=100;var netsize=256;var maxnetpos=netsize-1;var netbiasshift=4;var intbiasshift=16;var intbias=1<>betashift;var betagamma=intbias<>3;var radiusbiasshift=6;var radiusbias=1<>3);var i,v;for(i=0;i>=netbiasshift;network[i][1]>>=netbiasshift;network[i][2]>>=netbiasshift;network[i][3]=i}}function altersingle(alpha,i,b,g,r){network[i][0]-=alpha*(network[i][0]-b)/initalpha;network[i][1]-=alpha*(network[i][1]-g)/initalpha;network[i][2]-=alpha*(network[i][2]-r)/initalpha}function alterneigh(radius,i,b,g,r){var lo=Math.abs(i-radius);var hi=Math.min(i+radius,netsize);var j=i+1;var k=i-1;var m=1;var p,a;while(jlo){a=radpower[m++];if(jlo){p=network[k--];p[0]-=a*(p[0]-b)/alpharadbias;p[1]-=a*(p[1]-g)/alpharadbias;p[2]-=a*(p[2]-r)/alpharadbias}}}function contest(b,g,r){var bestd=~(1<<31);var bestbiasd=bestd;var bestpos=-1;var bestbiaspos=bestpos;var i,n,dist,biasdist,betafreq;for(i=0;i>intbiasshift-netbiasshift);if(biasdist>betashift;freq[i]-=betafreq;bias[i]+=betafreq<>1;for(j=previouscol+1;j>1;for(j=previouscol+1;j<256;j++)netindex[j]=maxnetpos}function inxsearch(b,g,r){var a,p,dist;var bestd=1e3;var best=-1;var i=netindex[g];var j=i-1;while(i=0){if(i=bestd)i=netsize;else{i++;if(dist<0)dist=-dist;a=p[0]-b;if(a<0)a=-a;dist+=a;if(dist=0){p=network[j];dist=g-p[1];if(dist>=bestd)j=-1;else{j--;if(dist<0)dist=-dist;a=p[0]-b;if(a<0)a=-a;dist+=a;if(dist>radiusbiasshift;if(rad<=1)rad=0;for(i=0;i=lengthcount)pix-=lengthcount;i++;if(delta===0)delta=1;if(i%delta===0){alpha-=alpha/alphadec;radius-=radius/radiusdec;rad=radius>>radiusbiasshift;if(rad<=1)rad=0;for(j=0;j 2 | 3 | 4 | 5 | 6 | 7 | 微信对话生成器 8 | 77 | 78 | 79 | 80 | 81 |
82 |
83 | 84 | 85 | 86 |

正在努力加载页面,请耐心等候...

87 |
88 |
89 | 90 | 91 | 92 | 93 | -------------------------------------------------------------------------------- /index.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 微信对话生成器 8 | 77 | 78 | 79 |
80 |
81 | 82 | 83 | 84 |

正在努力加载页面,请耐心等候...

85 |
86 |
87 | 88 | 89 | 90 | 91 | -------------------------------------------------------------------------------- /package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "vue3-wechat-tool", 3 | "version": "0.0.1", 4 | "description": "使用 Vite + Vue3 + AntDesignVue + Pinia 搭建的在线微信对话生成器", 5 | "author": "ele-cat", 6 | "license": "MIT", 7 | "homepage": "https://github.com/ele-cat/vue3-wechat-tool", 8 | "private": true, 9 | "type": "module", 10 | "scripts": { 11 | "serve": "vite", 12 | "build": "vite build", 13 | "preview": "vite preview" 14 | }, 15 | "dependencies": { 16 | "@vueuse/core": "^10.4.1", 17 | "ant-design-vue": "^4.0.2", 18 | "file-saver": "^2.0.5", 19 | "gif.js": "^0.2.0", 20 | "html2canvas": "^1.4.1", 21 | "jszip": "^3.10.1", 22 | "mitt": "^3.0.1", 23 | "pinia": "^2.1.6", 24 | "pinia-plugin-persist": "^1.0.0", 25 | "vue": "^3.3.4", 26 | "vue-advanced-cropper": "^2.8.8", 27 | "vue3-perfect-scrollbar": "^1.6.1" 28 | }, 29 | "devDependencies": { 30 | "@vitejs/plugin-vue": "^4.2.3", 31 | "less": "^4.2.0", 32 | "less-loader": "^11.1.3", 33 | "vite": "^4.4.5" 34 | } 35 | } 36 | -------------------------------------------------------------------------------- /public/favicon.ico: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Ele-Cat/vue3-wechat-tool/3626955435e1c241df7f4f225d06a72756cc806c/public/favicon.ico -------------------------------------------------------------------------------- /public/gif.worker.js: -------------------------------------------------------------------------------- 1 | // gif.worker.js 0.2.0 - https://github.com/jnordberg/gif.js 2 | (function e(t,n,r){function s(o,u){if(!n[o]){if(!t[o]){var a=typeof require=="function"&&require;if(!u&&a)return a(o,!0);if(i)return i(o,!0);var f=new Error("Cannot find module '"+o+"'");throw f.code="MODULE_NOT_FOUND",f}var l=n[o]={exports:{}};t[o][0].call(l.exports,function(e){var n=t[o][1][e];return s(n?n:e)},l,l.exports,e,t,n,r)}return n[o].exports}var i=typeof require=="function"&&require;for(var o=0;o=ByteArray.pageSize)this.newPage();this.pages[this.page][this.cursor++]=val};ByteArray.prototype.writeUTFBytes=function(string){for(var l=string.length,i=0;i=0)this.dispose=disposalCode};GIFEncoder.prototype.setRepeat=function(repeat){this.repeat=repeat};GIFEncoder.prototype.setTransparent=function(color){this.transparent=color};GIFEncoder.prototype.addFrame=function(imageData){this.image=imageData;this.colorTab=this.globalPalette&&this.globalPalette.slice?this.globalPalette:null;this.getImagePixels();this.analyzePixels();if(this.globalPalette===true)this.globalPalette=this.colorTab;if(this.firstFrame){this.writeLSD();this.writePalette();if(this.repeat>=0){this.writeNetscapeExt()}}this.writeGraphicCtrlExt();this.writeImageDesc();if(!this.firstFrame&&!this.globalPalette)this.writePalette();this.writePixels();this.firstFrame=false};GIFEncoder.prototype.finish=function(){this.out.writeByte(59)};GIFEncoder.prototype.setQuality=function(quality){if(quality<1)quality=1;this.sample=quality};GIFEncoder.prototype.setDither=function(dither){if(dither===true)dither="FloydSteinberg";this.dither=dither};GIFEncoder.prototype.setGlobalPalette=function(palette){this.globalPalette=palette};GIFEncoder.prototype.getGlobalPalette=function(){return this.globalPalette&&this.globalPalette.slice&&this.globalPalette.slice(0)||this.globalPalette};GIFEncoder.prototype.writeHeader=function(){this.out.writeUTFBytes("GIF89a")};GIFEncoder.prototype.analyzePixels=function(){if(!this.colorTab){this.neuQuant=new NeuQuant(this.pixels,this.sample);this.neuQuant.buildColormap();this.colorTab=this.neuQuant.getColormap()}if(this.dither){this.ditherPixels(this.dither.replace("-serpentine",""),this.dither.match(/-serpentine/)!==null)}else{this.indexPixels()}this.pixels=null;this.colorDepth=8;this.palSize=7;if(this.transparent!==null){this.transIndex=this.findClosest(this.transparent,true)}};GIFEncoder.prototype.indexPixels=function(imgq){var nPix=this.pixels.length/3;this.indexedPixels=new Uint8Array(nPix);var k=0;for(var j=0;j=0&&x1+x=0&&y1+y>16,(c&65280)>>8,c&255,used)};GIFEncoder.prototype.findClosestRGB=function(r,g,b,used){if(this.colorTab===null)return-1;if(this.neuQuant&&!used){return this.neuQuant.lookupRGB(r,g,b)}var c=b|g<<8|r<<16;var minpos=0;var dmin=256*256*256;var len=this.colorTab.length;for(var i=0,index=0;i=0){disp=dispose&7}disp<<=2;this.out.writeByte(0|disp|0|transp);this.writeShort(this.delay);this.out.writeByte(this.transIndex);this.out.writeByte(0)};GIFEncoder.prototype.writeImageDesc=function(){this.out.writeByte(44);this.writeShort(0);this.writeShort(0);this.writeShort(this.width);this.writeShort(this.height);if(this.firstFrame||this.globalPalette){this.out.writeByte(0)}else{this.out.writeByte(128|0|0|0|this.palSize)}};GIFEncoder.prototype.writeLSD=function(){this.writeShort(this.width);this.writeShort(this.height);this.out.writeByte(128|112|0|this.palSize);this.out.writeByte(0);this.out.writeByte(0)};GIFEncoder.prototype.writeNetscapeExt=function(){this.out.writeByte(33);this.out.writeByte(255);this.out.writeByte(11);this.out.writeUTFBytes("NETSCAPE2.0");this.out.writeByte(3);this.out.writeByte(1);this.writeShort(this.repeat);this.out.writeByte(0)};GIFEncoder.prototype.writePalette=function(){this.out.writeBytes(this.colorTab);var n=3*256-this.colorTab.length;for(var i=0;i>8&255)};GIFEncoder.prototype.writePixels=function(){var enc=new LZWEncoder(this.width,this.height,this.indexedPixels,this.colorDepth);enc.encode(this.out)};GIFEncoder.prototype.stream=function(){return this.out};module.exports=GIFEncoder},{"./LZWEncoder.js":2,"./TypedNeuQuant.js":3}],2:[function(require,module,exports){var EOF=-1;var BITS=12;var HSIZE=5003;var masks=[0,1,3,7,15,31,63,127,255,511,1023,2047,4095,8191,16383,32767,65535];function LZWEncoder(width,height,pixels,colorDepth){var initCodeSize=Math.max(2,colorDepth);var accum=new Uint8Array(256);var htab=new Int32Array(HSIZE);var codetab=new Int32Array(HSIZE);var cur_accum,cur_bits=0;var a_count;var free_ent=0;var maxcode;var clear_flg=false;var g_init_bits,ClearCode,EOFCode;function char_out(c,outs){accum[a_count++]=c;if(a_count>=254)flush_char(outs)}function cl_block(outs){cl_hash(HSIZE);free_ent=ClearCode+2;clear_flg=true;output(ClearCode,outs)}function cl_hash(hsize){for(var i=0;i=0){disp=hsize_reg-i;if(i===0)disp=1;do{if((i-=disp)<0)i+=hsize_reg;if(htab[i]===fcode){ent=codetab[i];continue outer_loop}}while(htab[i]>=0)}output(ent,outs);ent=c;if(free_ent<1<0){outs.writeByte(a_count);outs.writeBytes(accum,0,a_count);a_count=0}}function MAXCODE(n_bits){return(1<0)cur_accum|=code<=8){char_out(cur_accum&255,outs);cur_accum>>=8;cur_bits-=8}if(free_ent>maxcode||clear_flg){if(clear_flg){maxcode=MAXCODE(n_bits=g_init_bits);clear_flg=false}else{++n_bits;if(n_bits==BITS)maxcode=1<0){char_out(cur_accum&255,outs);cur_accum>>=8;cur_bits-=8}flush_char(outs)}}this.encode=encode}module.exports=LZWEncoder},{}],3:[function(require,module,exports){var ncycles=100;var netsize=256;var maxnetpos=netsize-1;var netbiasshift=4;var intbiasshift=16;var intbias=1<>betashift;var betagamma=intbias<>3;var radiusbiasshift=6;var radiusbias=1<>3);var i,v;for(i=0;i>=netbiasshift;network[i][1]>>=netbiasshift;network[i][2]>>=netbiasshift;network[i][3]=i}}function altersingle(alpha,i,b,g,r){network[i][0]-=alpha*(network[i][0]-b)/initalpha;network[i][1]-=alpha*(network[i][1]-g)/initalpha;network[i][2]-=alpha*(network[i][2]-r)/initalpha}function alterneigh(radius,i,b,g,r){var lo=Math.abs(i-radius);var hi=Math.min(i+radius,netsize);var j=i+1;var k=i-1;var m=1;var p,a;while(jlo){a=radpower[m++];if(jlo){p=network[k--];p[0]-=a*(p[0]-b)/alpharadbias;p[1]-=a*(p[1]-g)/alpharadbias;p[2]-=a*(p[2]-r)/alpharadbias}}}function contest(b,g,r){var bestd=~(1<<31);var bestbiasd=bestd;var bestpos=-1;var bestbiaspos=bestpos;var i,n,dist,biasdist,betafreq;for(i=0;i>intbiasshift-netbiasshift);if(biasdist>betashift;freq[i]-=betafreq;bias[i]+=betafreq<>1;for(j=previouscol+1;j>1;for(j=previouscol+1;j<256;j++)netindex[j]=maxnetpos}function inxsearch(b,g,r){var a,p,dist;var bestd=1e3;var best=-1;var i=netindex[g];var j=i-1;while(i=0){if(i=bestd)i=netsize;else{i++;if(dist<0)dist=-dist;a=p[0]-b;if(a<0)a=-a;dist+=a;if(dist=0){p=network[j];dist=g-p[1];if(dist>=bestd)j=-1;else{j--;if(dist<0)dist=-dist;a=p[0]-b;if(a<0)a=-a;dist+=a;if(dist>radiusbiasshift;if(rad<=1)rad=0;for(i=0;i=lengthcount)pix-=lengthcount;i++;if(delta===0)delta=1;if(i%delta===0){alpha-=alpha/alphadec;radius-=radius/radiusdec;rad=radius>>radiusbiasshift;if(rad<=1)rad=0;for(j=0;j 2 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 21 | 26 | 27 | 28 | 29 | 30 | 31 | 32 | 33 | 34 | 35 | 36 | 37 | 38 | 39 | 40 | 41 | 143 | 144 | 165 | -------------------------------------------------------------------------------- /src/assets/fonts/sf-pro-text_medium.woff2: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Ele-Cat/vue3-wechat-tool/3626955435e1c241df7f4f225d06a72756cc806c/src/assets/fonts/sf-pro-text_medium.woff2 -------------------------------------------------------------------------------- /src/assets/fonts/sf-pro-text_regular.woff2: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Ele-Cat/vue3-wechat-tool/3626955435e1c241df7f4f225d06a72756cc806c/src/assets/fonts/sf-pro-text_regular.woff2 -------------------------------------------------------------------------------- /src/assets/fonts/sf-pro-text_semibold.woff2: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Ele-Cat/vue3-wechat-tool/3626955435e1c241df7f4f225d06a72756cc806c/src/assets/fonts/sf-pro-text_semibold.woff2 -------------------------------------------------------------------------------- /src/assets/images/bar/ios-battery-charge-dark.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Ele-Cat/vue3-wechat-tool/3626955435e1c241df7f4f225d06a72756cc806c/src/assets/images/bar/ios-battery-charge-dark.png -------------------------------------------------------------------------------- /src/assets/images/bar/ios-battery-charge-light.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Ele-Cat/vue3-wechat-tool/3626955435e1c241df7f4f225d06a72756cc806c/src/assets/images/bar/ios-battery-charge-light.png -------------------------------------------------------------------------------- /src/assets/images/bar/ios-battery-dark.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Ele-Cat/vue3-wechat-tool/3626955435e1c241df7f4f225d06a72756cc806c/src/assets/images/bar/ios-battery-dark.png -------------------------------------------------------------------------------- /src/assets/images/bar/ios-battery-light.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Ele-Cat/vue3-wechat-tool/3626955435e1c241df7f4f225d06a72756cc806c/src/assets/images/bar/ios-battery-light.png -------------------------------------------------------------------------------- /src/assets/images/bar/ios-single-1-dark.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Ele-Cat/vue3-wechat-tool/3626955435e1c241df7f4f225d06a72756cc806c/src/assets/images/bar/ios-single-1-dark.png -------------------------------------------------------------------------------- /src/assets/images/bar/ios-single-1-light.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Ele-Cat/vue3-wechat-tool/3626955435e1c241df7f4f225d06a72756cc806c/src/assets/images/bar/ios-single-1-light.png -------------------------------------------------------------------------------- /src/assets/images/bar/ios-single-2-dark.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Ele-Cat/vue3-wechat-tool/3626955435e1c241df7f4f225d06a72756cc806c/src/assets/images/bar/ios-single-2-dark.png -------------------------------------------------------------------------------- /src/assets/images/bar/ios-single-2-light.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Ele-Cat/vue3-wechat-tool/3626955435e1c241df7f4f225d06a72756cc806c/src/assets/images/bar/ios-single-2-light.png -------------------------------------------------------------------------------- /src/assets/images/bar/ios-single-3-dark.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Ele-Cat/vue3-wechat-tool/3626955435e1c241df7f4f225d06a72756cc806c/src/assets/images/bar/ios-single-3-dark.png -------------------------------------------------------------------------------- /src/assets/images/bar/ios-single-3-light.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Ele-Cat/vue3-wechat-tool/3626955435e1c241df7f4f225d06a72756cc806c/src/assets/images/bar/ios-single-3-light.png -------------------------------------------------------------------------------- /src/assets/images/bar/ios-single-4-dark.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Ele-Cat/vue3-wechat-tool/3626955435e1c241df7f4f225d06a72756cc806c/src/assets/images/bar/ios-single-4-dark.png -------------------------------------------------------------------------------- /src/assets/images/bar/ios-single-4-light.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Ele-Cat/vue3-wechat-tool/3626955435e1c241df7f4f225d06a72756cc806c/src/assets/images/bar/ios-single-4-light.png -------------------------------------------------------------------------------- /src/assets/images/bar/ios-wifi-1-dark.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Ele-Cat/vue3-wechat-tool/3626955435e1c241df7f4f225d06a72756cc806c/src/assets/images/bar/ios-wifi-1-dark.png -------------------------------------------------------------------------------- /src/assets/images/bar/ios-wifi-1-light.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Ele-Cat/vue3-wechat-tool/3626955435e1c241df7f4f225d06a72756cc806c/src/assets/images/bar/ios-wifi-1-light.png -------------------------------------------------------------------------------- /src/assets/images/bar/ios-wifi-2-dark.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Ele-Cat/vue3-wechat-tool/3626955435e1c241df7f4f225d06a72756cc806c/src/assets/images/bar/ios-wifi-2-dark.png -------------------------------------------------------------------------------- /src/assets/images/bar/ios-wifi-2-light.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Ele-Cat/vue3-wechat-tool/3626955435e1c241df7f4f225d06a72756cc806c/src/assets/images/bar/ios-wifi-2-light.png -------------------------------------------------------------------------------- /src/assets/images/bar/ios-wifi-3-dark.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Ele-Cat/vue3-wechat-tool/3626955435e1c241df7f4f225d06a72756cc806c/src/assets/images/bar/ios-wifi-3-dark.png -------------------------------------------------------------------------------- /src/assets/images/bar/ios-wifi-3-light.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Ele-Cat/vue3-wechat-tool/3626955435e1c241df7f4f225d06a72756cc806c/src/assets/images/bar/ios-wifi-3-light.png -------------------------------------------------------------------------------- /src/assets/images/bottom/phone-bottom-bar-dark.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Ele-Cat/vue3-wechat-tool/3626955435e1c241df7f4f225d06a72756cc806c/src/assets/images/bottom/phone-bottom-bar-dark.png -------------------------------------------------------------------------------- /src/assets/images/bottom/phone-bottom-bar-light.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Ele-Cat/vue3-wechat-tool/3626955435e1c241df7f4f225d06a72756cc806c/src/assets/images/bottom/phone-bottom-bar-light.png -------------------------------------------------------------------------------- /src/assets/images/bottom/wechat-bottom-icon1-dark.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Ele-Cat/vue3-wechat-tool/3626955435e1c241df7f4f225d06a72756cc806c/src/assets/images/bottom/wechat-bottom-icon1-dark.png -------------------------------------------------------------------------------- /src/assets/images/bottom/wechat-bottom-icon1-light.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Ele-Cat/vue3-wechat-tool/3626955435e1c241df7f4f225d06a72756cc806c/src/assets/images/bottom/wechat-bottom-icon1-light.png -------------------------------------------------------------------------------- /src/assets/images/bottom/wechat-bottom-icon2-dark.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Ele-Cat/vue3-wechat-tool/3626955435e1c241df7f4f225d06a72756cc806c/src/assets/images/bottom/wechat-bottom-icon2-dark.png -------------------------------------------------------------------------------- /src/assets/images/bottom/wechat-bottom-icon2-light.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Ele-Cat/vue3-wechat-tool/3626955435e1c241df7f4f225d06a72756cc806c/src/assets/images/bottom/wechat-bottom-icon2-light.png -------------------------------------------------------------------------------- /src/assets/images/bottom/wechat-bottom-icon3-dark.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Ele-Cat/vue3-wechat-tool/3626955435e1c241df7f4f225d06a72756cc806c/src/assets/images/bottom/wechat-bottom-icon3-dark.png -------------------------------------------------------------------------------- /src/assets/images/bottom/wechat-bottom-icon3-light.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Ele-Cat/vue3-wechat-tool/3626955435e1c241df7f4f225d06a72756cc806c/src/assets/images/bottom/wechat-bottom-icon3-light.png -------------------------------------------------------------------------------- /src/assets/images/bottom/wechat-bottom-icon4-dark.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Ele-Cat/vue3-wechat-tool/3626955435e1c241df7f4f225d06a72756cc806c/src/assets/images/bottom/wechat-bottom-icon4-dark.png -------------------------------------------------------------------------------- /src/assets/images/bottom/wechat-bottom-icon4-light.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Ele-Cat/vue3-wechat-tool/3626955435e1c241df7f4f225d06a72756cc806c/src/assets/images/bottom/wechat-bottom-icon4-light.png -------------------------------------------------------------------------------- /src/assets/images/content/wechat-audio-dark.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Ele-Cat/vue3-wechat-tool/3626955435e1c241df7f4f225d06a72756cc806c/src/assets/images/content/wechat-audio-dark.png -------------------------------------------------------------------------------- /src/assets/images/content/wechat-audio-light.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Ele-Cat/vue3-wechat-tool/3626955435e1c241df7f4f225d06a72756cc806c/src/assets/images/content/wechat-audio-light.png -------------------------------------------------------------------------------- /src/assets/images/content/wechat-redp-icon1.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Ele-Cat/vue3-wechat-tool/3626955435e1c241df7f4f225d06a72756cc806c/src/assets/images/content/wechat-redp-icon1.png -------------------------------------------------------------------------------- /src/assets/images/content/wechat-trans-icon1.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Ele-Cat/vue3-wechat-tool/3626955435e1c241df7f4f225d06a72756cc806c/src/assets/images/content/wechat-trans-icon1.png -------------------------------------------------------------------------------- /src/assets/images/content/wechat-trans-icon2.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Ele-Cat/vue3-wechat-tool/3626955435e1c241df7f4f225d06a72756cc806c/src/assets/images/content/wechat-trans-icon2.png -------------------------------------------------------------------------------- /src/assets/images/content/wechat-trans-icon3.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Ele-Cat/vue3-wechat-tool/3626955435e1c241df7f4f225d06a72756cc806c/src/assets/images/content/wechat-trans-icon3.png -------------------------------------------------------------------------------- /src/assets/images/content/wechat-trans-icon4.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Ele-Cat/vue3-wechat-tool/3626955435e1c241df7f4f225d06a72756cc806c/src/assets/images/content/wechat-trans-icon4.png -------------------------------------------------------------------------------- /src/assets/images/content/wechat-video-dark.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Ele-Cat/vue3-wechat-tool/3626955435e1c241df7f4f225d06a72756cc806c/src/assets/images/content/wechat-video-dark.png -------------------------------------------------------------------------------- /src/assets/images/content/wechat-video-light.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Ele-Cat/vue3-wechat-tool/3626955435e1c241df7f4f225d06a72756cc806c/src/assets/images/content/wechat-video-light.png -------------------------------------------------------------------------------- /src/assets/images/content/wechat-voice-icon1-dark.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Ele-Cat/vue3-wechat-tool/3626955435e1c241df7f4f225d06a72756cc806c/src/assets/images/content/wechat-voice-icon1-dark.png -------------------------------------------------------------------------------- /src/assets/images/content/wechat-voice-icon1-light.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Ele-Cat/vue3-wechat-tool/3626955435e1c241df7f4f225d06a72756cc806c/src/assets/images/content/wechat-voice-icon1-light.png -------------------------------------------------------------------------------- /src/assets/images/content/wechat-voice-icon2-dark.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Ele-Cat/vue3-wechat-tool/3626955435e1c241df7f4f225d06a72756cc806c/src/assets/images/content/wechat-voice-icon2-dark.png -------------------------------------------------------------------------------- /src/assets/images/content/wechat-voice-icon2-light.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Ele-Cat/vue3-wechat-tool/3626955435e1c241df7f4f225d06a72756cc806c/src/assets/images/content/wechat-voice-icon2-light.png -------------------------------------------------------------------------------- /src/assets/images/nav/wechat-nav-back-dark.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Ele-Cat/vue3-wechat-tool/3626955435e1c241df7f4f225d06a72756cc806c/src/assets/images/nav/wechat-nav-back-dark.png -------------------------------------------------------------------------------- /src/assets/images/nav/wechat-nav-back-light.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Ele-Cat/vue3-wechat-tool/3626955435e1c241df7f4f225d06a72756cc806c/src/assets/images/nav/wechat-nav-back-light.png -------------------------------------------------------------------------------- /src/assets/images/nav/wechat-nav-right-dark.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Ele-Cat/vue3-wechat-tool/3626955435e1c241df7f4f225d06a72756cc806c/src/assets/images/nav/wechat-nav-right-dark.png -------------------------------------------------------------------------------- /src/assets/images/nav/wechat-nav-right-light.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Ele-Cat/vue3-wechat-tool/3626955435e1c241df7f4f225d06a72756cc806c/src/assets/images/nav/wechat-nav-right-light.png -------------------------------------------------------------------------------- /src/assets/images/nav/wechat-trans-earphone-dark.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Ele-Cat/vue3-wechat-tool/3626955435e1c241df7f4f225d06a72756cc806c/src/assets/images/nav/wechat-trans-earphone-dark.png -------------------------------------------------------------------------------- /src/assets/images/nav/wechat-trans-earphone-light.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Ele-Cat/vue3-wechat-tool/3626955435e1c241df7f4f225d06a72756cc806c/src/assets/images/nav/wechat-trans-earphone-light.png -------------------------------------------------------------------------------- /src/components/ConfigAppearance.vue: -------------------------------------------------------------------------------- 1 | 82 | 83 | 146 | 147 | -------------------------------------------------------------------------------- /src/components/ConfigChat.vue: -------------------------------------------------------------------------------- 1 | 45 | 46 | 80 | 81 | 178 | 179 | -------------------------------------------------------------------------------- /src/components/ConfigInstructions.vue: -------------------------------------------------------------------------------- 1 | 4 | 5 | 8 | 9 | -------------------------------------------------------------------------------- /src/components/ConfigTemplate.vue: -------------------------------------------------------------------------------- 1 | 37 | 38 | 91 | 92 | 101 | 102 | -------------------------------------------------------------------------------- /src/components/WtContent.vue: -------------------------------------------------------------------------------- 1 | 24 | 25 | 57 | 58 | -------------------------------------------------------------------------------- /src/components/WtHeader.vue: -------------------------------------------------------------------------------- 1 | 7 | 8 | 11 | 12 | -------------------------------------------------------------------------------- /src/components/WtSider.vue: -------------------------------------------------------------------------------- 1 | 17 | 18 | 54 | 55 | -------------------------------------------------------------------------------- /src/components/common/ContextMenu.vue: -------------------------------------------------------------------------------- 1 | 13 | 14 | 146 | 147 | -------------------------------------------------------------------------------- /src/components/common/CustomUpload.vue: -------------------------------------------------------------------------------- 1 | 15 | 16 | 62 | 63 | -------------------------------------------------------------------------------- /src/components/common/Disclaimers.vue: -------------------------------------------------------------------------------- 1 | 25 | 26 | 39 | 40 | 55 | 56 | -------------------------------------------------------------------------------- /src/components/common/Emoji.vue: -------------------------------------------------------------------------------- 1 | 9 | 10 | 19 | 20 | 41 | -------------------------------------------------------------------------------- /src/components/common/ImageEditor.vue: -------------------------------------------------------------------------------- 1 | 52 | 53 | 187 | 188 | -------------------------------------------------------------------------------- /src/components/common/Instructions.vue: -------------------------------------------------------------------------------- 1 | 20 | 21 | 38 | 39 | -------------------------------------------------------------------------------- /src/components/common/IsPhone.vue: -------------------------------------------------------------------------------- 1 | 7 | 8 | 20 | 21 | -------------------------------------------------------------------------------- /src/components/common/Tutorial.vue: -------------------------------------------------------------------------------- 1 | 32 | 33 | 38 | 39 | -------------------------------------------------------------------------------- /src/components/common/UserManage.vue: -------------------------------------------------------------------------------- 1 | 31 | 32 | 85 | 86 | 97 | 98 | -------------------------------------------------------------------------------- /src/components/phone/PhoneBar.vue: -------------------------------------------------------------------------------- 1 | 12 | 13 | 21 | 22 | 150 | -------------------------------------------------------------------------------- /src/components/phone/PhoneBody.vue: -------------------------------------------------------------------------------- 1 | 94 | 95 | 144 | 145 | -------------------------------------------------------------------------------- /src/components/phone/PhoneBottom.vue: -------------------------------------------------------------------------------- 1 | 14 | 15 | 45 | 46 | 162 | -------------------------------------------------------------------------------- /src/components/phone/PhoneGenerate.vue: -------------------------------------------------------------------------------- 1 | 16 | 17 | 24 | 25 | 60 | -------------------------------------------------------------------------------- /src/components/phone/PhoneNav.vue: -------------------------------------------------------------------------------- 1 | 15 | 16 | 33 | 34 | 137 | -------------------------------------------------------------------------------- /src/components/phone/PhoneTools.vue: -------------------------------------------------------------------------------- 1 | 15 | 16 | 39 | 40 | -------------------------------------------------------------------------------- /src/components/phone/generate/GeneConfig.vue: -------------------------------------------------------------------------------- 1 | 30 | 31 | -------------------------------------------------------------------------------- /src/components/phone/generate/GeneGif.vue: -------------------------------------------------------------------------------- 1 | 19 | 20 | -------------------------------------------------------------------------------- /src/components/phone/generate/GenePng.vue: -------------------------------------------------------------------------------- 1 | 19 | 20 | -------------------------------------------------------------------------------- /src/components/phone/generate/GeneTemplate.vue: -------------------------------------------------------------------------------- 1 | 26 | 27 | -------------------------------------------------------------------------------- /src/components/phone/generate/GeneVideo.vue: -------------------------------------------------------------------------------- 1 | 21 | 22 | 112 | 113 | -------------------------------------------------------------------------------- /src/global.less: -------------------------------------------------------------------------------- 1 | :root { 2 | scroll-behavior: smooth; 3 | // --theme-color: #e8a95b; 4 | --theme-color: #FD6585; 5 | --light-bg-color: #EDEDED; 6 | --light-text-color: #1A1A1A; 7 | --dark-bg-color: #232323; 8 | --dark-text-color: snow; 9 | } 10 | 11 | #app { 12 | user-select: none; 13 | max-height: 100vh; 14 | overflow: hidden; 15 | // font-family: 'SF Pro', 'PingFang SC'; 16 | } 17 | 18 | @font-face { 19 | font-family: SF Pro; 20 | font-style: normal; 21 | font-weight: 600; 22 | src: url(./assets/fonts/sf-pro-text_semibold.woff2) format("woff2"); 23 | } 24 | @font-face { 25 | font-family: SF Pro; 26 | font-style: normal; 27 | font-weight: 500; 28 | src: url(./assets/fonts/sf-pro-text_medium.woff2) format("woff2"); 29 | } 30 | @font-face { 31 | font-family: SF Pro; 32 | font-style: normal; 33 | font-weight: 400; 34 | src: url(./assets/fonts/sf-pro-text_regular.woff2) format("woff2"); 35 | } 36 | 37 | // 禁止图片被拖拽 38 | img { 39 | // pointer-events: none; 40 | -webkit-user-drag: none; 41 | // user-drag: none; 42 | -webkit-user-select: none; 43 | -moz-user-select: none; 44 | -ms-user-select: none; 45 | user-select: none; 46 | } 47 | 48 | // 设定滚轮 49 | ::-webkit-scrollbar { 50 | width: 8px; 51 | height: 8px; 52 | } 53 | ::-webkit-scrollbar-thumb { 54 | border-radius: 4px; 55 | box-shadow: inset 0 0 5px #cac8c6; 56 | background: #cac8c6; 57 | } 58 | ::-webkit-scrollbar-track { 59 | background: 0 0; 60 | border-radius: 1px; 61 | } 62 | 63 | .ps { 64 | position: relative; 65 | height: 100%; 66 | overflow-y: hidden; 67 | } 68 | 69 | .ps .ps__rail-x:hover, .ps .ps__rail-y:hover, .ps .ps__rail-x:focus, .ps .ps__rail-y:focus, .ps .ps__rail-x.ps--clicking, .ps .ps__rail-y.ps--clicking { 70 | background-color: transparent !important; 71 | } 72 | 73 | .ps__rail-y:hover > .ps__thumb-y, .ps__rail-y:focus > .ps__thumb-y, .ps__rail-y.ps--clicking .ps__thumb-y { 74 | width: 8px !important; 75 | } 76 | 77 | .ant-form-item { 78 | margin-bottom: 14px; 79 | } 80 | 81 | .default-loading { 82 | flex: 1; 83 | height: 136px; 84 | display: flex; 85 | flex-direction: column; 86 | justify-content: center; 87 | align-items: center; 88 | } 89 | 90 | .form-tip { 91 | position: absolute; 92 | font-size: 12px; 93 | color: gray; 94 | } -------------------------------------------------------------------------------- /src/hooks/useAutoScrollBottom.js: -------------------------------------------------------------------------------- 1 | import { onMounted, watch, nextTick } from "vue"; 2 | import eventBus from '@/utils/eventBus'; 3 | import useStore from "@/store"; 4 | const { useChatStore } = useStore(); 5 | 6 | /** 7 | * 执行本方法可以让盒子自动滚动至底 8 | * @param {ref} component ref绑定的dom 9 | */ 10 | export default function useAutoScrollBottom(component) { 11 | // watch(() => useChatStore.chatList, () => { 12 | // toBottom(); 13 | // }, { 14 | // deep: true, 15 | // }) 16 | 17 | onMounted(() => { 18 | toBottom(); 19 | 20 | eventBus.on("sentChat", () => { 21 | toBottom(); 22 | }) 23 | }); 24 | 25 | const toBottom = () => { 26 | if (!component || !component.value) return; 27 | nextTick(() => { 28 | component.value.scrollTop = component.value.scrollHeight; 29 | }) 30 | }; 31 | 32 | return { 33 | toBottom, 34 | } 35 | } 36 | -------------------------------------------------------------------------------- /src/hooks/useHtmlToImage.js: -------------------------------------------------------------------------------- 1 | import { ref } from 'vue'; 2 | import html2canvas from 'html2canvas'; 3 | import GIF from 'gif.js'; 4 | 5 | export function useHtmlToImage() { 6 | const imageUrl = ref(''); 7 | 8 | const captureHtmlToImage = async (element, params = {}) => { 9 | const canvas = await html2canvas(element, {...params}); 10 | imageUrl.value = canvas.toDataURL(); 11 | }; 12 | 13 | return { 14 | imageUrl, 15 | captureHtmlToImage, 16 | }; 17 | } 18 | 19 | export function useHtmlToGif() { 20 | const gifUrl = ref(''); 21 | 22 | const captureHtmlToGif = async (element) => { 23 | const canvas = await html2canvas(element); 24 | // 创建一个 GIF 实例 25 | const gif = new GIF(); 26 | // 将 Canvas 添加到 GIF 帧中 27 | gif.addFrame(canvas, { delay: 2000, copy: false, }); 28 | // 完成 GIF 编码 29 | gif.on('finished', (blob) => { 30 | // 创建 GIF 对象的 URL 31 | const url = URL.createObjectURL(blob); 32 | // 更新组件数据以显示 GIF 33 | gifUrl.value = url; 34 | }); 35 | 36 | // 开始编码 GIF 37 | gif.render(); 38 | }; 39 | 40 | return { 41 | gifUrl, 42 | captureHtmlToGif, 43 | }; 44 | } -------------------------------------------------------------------------------- /src/main.js: -------------------------------------------------------------------------------- 1 | import { createApp } from "vue"; 2 | import pinia from "@/store/pinia"; 3 | import App from "./App.vue"; 4 | 5 | import Antd from "ant-design-vue"; 6 | import "ant-design-vue/dist/reset.css"; 7 | import "./global.less"; 8 | 9 | import PerfectScrollbar from 'vue3-perfect-scrollbar' 10 | import 'vue3-perfect-scrollbar/dist/vue3-perfect-scrollbar.css' 11 | const app = createApp(App); 12 | 13 | app.use(pinia); 14 | app.use(Antd); 15 | app.use(PerfectScrollbar, { 16 | watchOptions: true, 17 | options: { 18 | minScrollbarLength: 38, // 设定最小滚动条高度 19 | // maxScrollbarLength: 200, // 设定最大滚动条高度 20 | } 21 | }); 22 | app.mount("#app"); 23 | -------------------------------------------------------------------------------- /src/store/index.js: -------------------------------------------------------------------------------- 1 | import { useSystemStore } from "./modules/system"; 2 | import { useChatStore } from "./modules/chat"; 3 | import { useUserStore } from "./modules/user"; 4 | import { useTemplateStore } from "./modules/template"; 5 | import { useContextMenuStore } from "./modules/contextMenu"; 6 | 7 | // 将store统一到一起再分发 8 | const useStore = () => ({ 9 | useSystemStore: useSystemStore(), 10 | useChatStore: useChatStore(), 11 | useUserStore: useUserStore(), 12 | useTemplateStore: useTemplateStore(), 13 | useContextMenuStore: useContextMenuStore(), 14 | }); 15 | 16 | export default useStore -------------------------------------------------------------------------------- /src/store/modules/chat.js: -------------------------------------------------------------------------------- 1 | import { defineStore } from "pinia"; 2 | import eventBus from '@/utils/eventBus'; 3 | import { useUserStore } from "./user"; 4 | 5 | export const useChatStore = defineStore("toolChat", { 6 | state: () => { 7 | return { 8 | chatList: [], // 聊天列表 9 | activeType: "text", 10 | inputText: "", 11 | generateConfig: { 12 | minInterval: 1500, 13 | maxInterval: 3000, 14 | }, 15 | }; 16 | }, 17 | getters: { 18 | /** 19 | * 根据角色返回已发送消息列表 20 | * @returns 21 | */ 22 | sendList() { 23 | let sendList = this.chatList.filter(chat => chat.role === useUserStore().activeRole).map(chat => { 24 | return { 25 | label: chat.content || content, 26 | value: chat.id, 27 | disabled: chat.received, 28 | } 29 | }); 30 | return sendList; 31 | } 32 | }, 33 | actions: { 34 | // 将某条消息置为已接收 35 | receiveChat(chatId) { 36 | this.chatList.map(chat => { 37 | if (chat.id === chatId) { 38 | chat.received = true; 39 | } 40 | }) 41 | }, 42 | // 发送消息 43 | sentChat(chatInfo) { 44 | this.chatList.push({ 45 | id: "chat-" + Date.now(), 46 | user: useUserStore().activeUser, 47 | ...chatInfo, 48 | }) 49 | eventBus.emit("sentChat"); 50 | }, 51 | // 修改消息 52 | editChat(chatInfo) { 53 | const editIndex = this.chatList.findIndex(chat => chat.id === chatInfo.id); 54 | this.chatList.splice(editIndex, 1, chatInfo); 55 | }, 56 | }, 57 | persist: { 58 | enabled: true, 59 | strategies: [ 60 | { 61 | storage: localStorage, 62 | paths: ["chatList", "activeType", "generateConfig"], 63 | }, 64 | ], 65 | }, 66 | }); 67 | -------------------------------------------------------------------------------- /src/store/modules/contextMenu.js: -------------------------------------------------------------------------------- 1 | import { defineStore } from "pinia"; 2 | 3 | export const useContextMenuStore = defineStore("toolContextMenu", { 4 | state: () => { 5 | return { 6 | menuVisible: false, // 是否显示右键菜单 7 | menuLeft: 0, // 菜单位置横坐标 8 | menuTop: 0, // 菜单位置纵坐标 9 | activeChatId: "", 10 | }; 11 | }, 12 | actions: { 13 | // 显示右键菜单 14 | showContextMenu(clientX, clientY, chatId) { 15 | this.activeChatId = chatId; 16 | this.menuLeft = clientX; 17 | this.menuTop = clientY; 18 | this.menuVisible = true; 19 | }, 20 | // 隐藏右键菜单 21 | hideContextMenu() { 22 | this.menuVisible = false; 23 | }, 24 | }, 25 | }); 26 | -------------------------------------------------------------------------------- /src/store/modules/system.js: -------------------------------------------------------------------------------- 1 | import { defineStore } from "pinia"; 2 | import _ from "lodash"; 3 | const appearance = { 4 | model: "ios", 5 | darkMode: false, 6 | networkType: "wifi", 7 | wifiSignal: "3", 8 | phoneSignal: "4", 9 | phoneTimeHour: "12", 10 | phoneTimeMinute: "21", 11 | timeFollowSystem: false, 12 | isCharging: false, 13 | phoneBattery: 60, 14 | earphoneMode: true, 15 | unreadMessages: 1, 16 | chatTitle: "微信对话", 17 | showChatName: false, 18 | voiceMode: false, 19 | syncInputText: true, 20 | chatBackground: "", 21 | } 22 | 23 | export const useSystemStore = defineStore("toolSystem", { 24 | state: () => { 25 | return { 26 | activeMenu: "appearance", // 当前聚焦的工具栏目 27 | appearance: _.cloneDeep(appearance), 28 | phoneWidth: 1125, 29 | phoneHeight: 2436, 30 | phoneScale: 1, 31 | hadDisclaimer: false, // 已经确认过声明 32 | qqGroupLink: "http://qm.qq.com/cgi-bin/qm/qr?_wv=1027&k=FBr4JIxIckrUqgDK-rbdMkoQYfJT4BCs&authKey=Dl1dUP8%2BXRNefHTYG38DyEi3CAOf20Pc8yyIJwKQ7HlP5WX7nYhURs2vVtmttNHX&noverify=0&group_code=887911914", // 跳转加群链接 33 | }; 34 | }, 35 | actions: { 36 | resetAppearance() { 37 | this.appearance = _.cloneDeep(appearance) 38 | }, 39 | }, 40 | persist: { 41 | enabled: true, 42 | strategies: [ 43 | { 44 | storage: localStorage, 45 | }, 46 | ], 47 | }, 48 | }); 49 | -------------------------------------------------------------------------------- /src/store/modules/template.js: -------------------------------------------------------------------------------- 1 | import { defineStore } from "pinia"; 2 | 3 | export const useTemplateStore = defineStore("toolTemplate", { 4 | state: () => { 5 | return { 6 | list: [], 7 | }; 8 | }, 9 | actions: { 10 | // 新增聊天模板 11 | add(params) { 12 | this.list.unshift({ 13 | id: `template-${Date.now()}`, 14 | ...params 15 | }) 16 | }, 17 | delete(id) { 18 | this.list = this.list.filter(item => item.id != id); 19 | }, 20 | }, 21 | persist: { 22 | enabled: true, 23 | strategies: [ 24 | { 25 | storage: localStorage, 26 | }, 27 | ], 28 | }, 29 | }); 30 | -------------------------------------------------------------------------------- /src/store/modules/user.js: -------------------------------------------------------------------------------- 1 | import { defineStore } from "pinia"; 2 | import { otherAvatar } from "@/utils/avatar"; 3 | 4 | export const useUserStore = defineStore("toolUser", { 5 | state: () => { 6 | return { 7 | selectedOther: "", 8 | userList: [], 9 | activeUserId: "", 10 | }; 11 | }, 12 | getters: { 13 | activeRole() { 14 | return this.activeUserId === "user-0" ? "own" : "other"; 15 | }, 16 | ownInfo() { 17 | return this.userList[0]; 18 | }, 19 | activeUser() { 20 | const user = this.userList.find(user => user.id === this.activeUserId) || {}; 21 | return user; 22 | }, 23 | }, 24 | actions: { 25 | addUser() { 26 | this.userList.push({ 27 | nickname: "微信用户", 28 | // avatar: otherAvatar, 29 | role: "other", 30 | id: "user-" + Date.now(), 31 | }) 32 | }, 33 | selectUser(id) { 34 | this.activeUserId = id; 35 | }, 36 | deleteUser(id) { 37 | this.userList = this.userList.filter(user => user.id != id); 38 | }, 39 | }, 40 | persist: { 41 | enabled: true, 42 | strategies: [ 43 | { 44 | storage: localStorage, 45 | }, 46 | ], 47 | }, 48 | }); 49 | -------------------------------------------------------------------------------- /src/store/pinia.js: -------------------------------------------------------------------------------- 1 | import { createPinia } from "pinia"; 2 | import piniaPluginPersist from "pinia-plugin-persist"; 3 | 4 | // 创建pinia实例 5 | const pinia = createPinia(); 6 | // pinia持久化 7 | pinia.use(piniaPluginPersist); 8 | 9 | export default pinia; 10 | -------------------------------------------------------------------------------- /src/utils/enum.js: -------------------------------------------------------------------------------- 1 | export const models = [ 2 | { 3 | label: "安卓", 4 | value: "android", 5 | width: 1224, 6 | height: 2700, 7 | }, 8 | { 9 | label: "苹果", 10 | value: "ios", 11 | width: 1125, 12 | height: 2436, 13 | }, 14 | ]; 15 | // iPhoneX 16 | // 分辨率: 1125x2436 17 | 18 | // iPhoneXR 19 | // 分辨率: 828x1792 20 | 21 | // iPhoneXs Max 22 | // 分辨率: 1242x2688 23 | 24 | // iPhone11 25 | // 分辨率: 828x1792 26 | 27 | // iPhone11 Pro 28 | // 分辨率: 1125x2436 29 | 30 | // iPhone12 31 | // 分辨率: 1170x2532 32 | 33 | // iPhone12 Mini 34 | // 分辨率: 1080x2340 35 | 36 | // iPhone11 Pro Max 37 | // 分辨率: 1242x2688 38 | 39 | // iPhone13 Mini 40 | // 分辨率: 1080x2340 41 | 42 | // iPhone13 43 | // 分辨率: 1170x2532 44 | 45 | // iPhone13 Pro Max 46 | // 分辨率: 1242x2688 47 | 48 | // iPhone14 Pro 49 | // 分辨率: 1179x2556 50 | 51 | // iPhone14 Pro Max 52 | // 分辨率: 1290x2796 53 | 54 | // --- 55 | 56 | // Mate40 57 | // 分辨率: 1080x2376 58 | 59 | // Mate40pro 60 | // 分辨率: 1200x2640 61 | 62 | // Nova8 63 | // 分辨率: 1080x2340 64 | 65 | // Mi10 66 | // 分辨率: 1080x2340 67 | 68 | // Mi11 69 | // 分辨率: 1440x3200 70 | 71 | export const networkTypes = [ 72 | { 73 | label: "Wifi", 74 | value: "wifi", 75 | }, 76 | { 77 | label: "3G", 78 | value: "3", 79 | }, 80 | { 81 | label: "4G", 82 | value: "4", 83 | }, 84 | { 85 | label: "5G", 86 | value: "5", 87 | }, 88 | ]; 89 | 90 | export const wifiSignals = [ 91 | { 92 | label: "1格", 93 | value: "1", 94 | }, 95 | { 96 | label: "2格", 97 | value: "2", 98 | }, 99 | { 100 | label: "3格", 101 | value: "3", 102 | }, 103 | ]; 104 | 105 | export const phoneSignals = [ 106 | { 107 | label: "1格", 108 | value: "1", 109 | }, 110 | { 111 | label: "2格", 112 | value: "2", 113 | }, 114 | { 115 | label: "3格", 116 | value: "3", 117 | }, 118 | { 119 | label: "4格", 120 | value: "4", 121 | }, 122 | ]; 123 | 124 | export const addTypes = [ 125 | { 126 | label: "文本", 127 | value: "text", 128 | }, 129 | { 130 | label: "图片", 131 | value: "image", 132 | }, 133 | { 134 | label: "转账", 135 | value: "transferAccounts", 136 | }, 137 | { 138 | label: "红包", 139 | value: "redEnvelope", 140 | }, 141 | { 142 | label: "语音", 143 | value: "voice", 144 | }, 145 | { 146 | label: "音视频", 147 | value: "avInvite", 148 | }, 149 | { 150 | label: "名片", 151 | value: "businessCard", 152 | }, 153 | { 154 | label: "拍一拍", 155 | value: "takeAPat", 156 | }, 157 | { 158 | label: "时间", 159 | value: "time", 160 | }, 161 | { 162 | label: "撤回", 163 | value: "revoke", 164 | }, 165 | { 166 | label: "系统消息", 167 | value: "system", 168 | }, 169 | ] 170 | 171 | export const weeks = [ 172 | { 173 | label: "周一", 174 | value: "周一", 175 | }, 176 | { 177 | label: "周二", 178 | value: "周二", 179 | }, 180 | { 181 | label: "周三", 182 | value: "周三", 183 | }, 184 | { 185 | label: "周四", 186 | value: "周四", 187 | }, 188 | { 189 | label: "周五", 190 | value: "周五", 191 | }, 192 | { 193 | label: "周六", 194 | value: "周六", 195 | }, 196 | { 197 | label: "周日", 198 | value: "周日", 199 | }, 200 | { 201 | label: "昨天", 202 | value: "昨天", 203 | }, 204 | ]; 205 | 206 | export const morningAfternoon = [ 207 | { 208 | label: "上午", 209 | value: "上午", 210 | }, 211 | { 212 | label: "下午", 213 | value: "下午", 214 | }, 215 | ] 216 | 217 | export const emojiList = [ 218 | "微笑", 219 | "撇嘴", 220 | "色", 221 | "发呆", 222 | "得意", 223 | "流泪", 224 | "害羞", 225 | "闭嘴", 226 | "睡", 227 | "大哭", 228 | "尴尬", 229 | "发怒", 230 | "调皮", 231 | "呲牙", 232 | "惊讶", 233 | "难过", 234 | "囧", 235 | "抓狂", 236 | "吐", 237 | "偷笑", 238 | "愉快", 239 | "白眼", 240 | "傲慢", 241 | "困", 242 | "惊恐", 243 | "憨笑", 244 | "悠闲", 245 | "咒骂", 246 | "疑问", 247 | "嘘", 248 | "晕", 249 | "衰", 250 | "骷髅", 251 | "敲打", 252 | "再见", 253 | "擦汗", 254 | "抠鼻", 255 | "鼓掌", 256 | "坏笑", 257 | "右哼哼", 258 | "鄙视", 259 | "委屈", 260 | "快哭了", 261 | "阴险", 262 | "亲亲", 263 | "可怜", 264 | "笑脸", 265 | "生病", 266 | "脸红", 267 | "破涕为笑", 268 | "恐惧", 269 | "失望", 270 | "无语", 271 | "嘿哈", 272 | "捂脸", 273 | "奸笑", 274 | "机智", 275 | "皱眉", 276 | "耶", 277 | "吃瓜", 278 | "加油", 279 | "汗", 280 | "天啊", 281 | "Emm", 282 | "社会社会", 283 | "旺财", 284 | "好的", 285 | "打脸", 286 | "哇", 287 | "翻白眼", 288 | "666", 289 | "让我看看", 290 | "叹气", 291 | "苦涩", 292 | "裂开", 293 | "嘴唇", 294 | "爱心", 295 | "心碎", 296 | "拥抱", 297 | "强", 298 | "弱", 299 | "握手", 300 | "胜利", 301 | "抱拳", 302 | "勾引", 303 | "拳头", 304 | "OK", 305 | "合十", 306 | "啤酒", 307 | "咖啡", 308 | "蛋糕", 309 | "玫瑰", 310 | "凋谢", 311 | "菜刀", 312 | "炸弹", 313 | "便便", 314 | "月亮", 315 | "太阳", 316 | "庆祝", 317 | "礼物", 318 | "红包", 319 | "發", 320 | "福", 321 | "烟花", 322 | "猪头", 323 | "跳跳", 324 | "发抖", 325 | "转圈", 326 | ] 327 | 328 | export const avInviteTypes = [ 329 | { 330 | label: "音频邀请", 331 | value: "audio", 332 | }, 333 | { 334 | label: "视频邀请", 335 | value: "video", 336 | }, 337 | ] 338 | 339 | export const avInviteStates = [ 340 | { 341 | label: "通话完成", 342 | value: "success", 343 | }, 344 | { 345 | label: "已取消", 346 | value: "cancel", 347 | }, 348 | { 349 | label: "忙线中", 350 | value: "busy", 351 | }, 352 | { 353 | label: "已拒绝", 354 | value: "reject", 355 | }, 356 | ] 357 | 358 | export const patRoles = [ 359 | { 360 | label: "对方", 361 | value: "other", 362 | }, 363 | { 364 | label: "自己", 365 | value: "own", 366 | }, 367 | ] 368 | 369 | export const ynEnums = [ 370 | { 371 | label: "是", 372 | value: true, 373 | }, 374 | { 375 | label: "否", 376 | value: false, 377 | }, 378 | ] -------------------------------------------------------------------------------- /src/utils/eventBus.js: -------------------------------------------------------------------------------- 1 | import mitt from 'mitt'; 2 | 3 | const eventBus = mitt(); 4 | 5 | export default eventBus; -------------------------------------------------------------------------------- /src/utils/feedback.js: -------------------------------------------------------------------------------- 1 | import { message, notification } from "ant-design-vue"; 2 | 3 | // 在浏览器中上部的提示 4 | export const toast = ({ 5 | type = "success", 6 | content = "提示语", 7 | duration = 3, 8 | }) => { 9 | message.open({ 10 | type, 11 | content, 12 | duration, 13 | }); 14 | }; 15 | 16 | // 在浏览器右上角的提示 17 | export const notify = ({ 18 | type = "success", 19 | title = "提示", 20 | content = "内容", 21 | duration = 3, 22 | }) => { 23 | notification.open({ 24 | type, 25 | message: title, 26 | description: content, 27 | duration, 28 | }); 29 | }; 30 | -------------------------------------------------------------------------------- /src/utils/utils.js: -------------------------------------------------------------------------------- 1 | /** 2 | * 将图片文件转换为 Base64 格式 3 | * @param {File} file - 图片文件对象 4 | * @returns {Promise} - 返回 Promise 对象 5 | */ 6 | export function fileToBase64(file) { 7 | return new Promise((resolve, reject) => { 8 | const reader = new FileReader(); 9 | reader.readAsDataURL(file); 10 | reader.onload = () => resolve(reader.result); 11 | reader.onerror = error => reject(error); 12 | }); 13 | } 14 | 15 | export async function urlToBase64(url) { 16 | return new Promise(async (resolve, reject) => { 17 | try { 18 | const response = await fetch(url); 19 | if (response.ok) { 20 | const reader = new FileReader(); 21 | const blob = await response.blob(); 22 | reader.onloadend = () => resolve(reader.result); 23 | reader.readAsDataURL(blob); 24 | } else { 25 | throw new Error('图片加载失败'); 26 | } 27 | } catch (error) { 28 | console.error(error); 29 | } 30 | }); 31 | } 32 | 33 | /** 34 | * 获取时分下拉 35 | * @param {Number} num 36 | * @returns 37 | */ 38 | export function toArr(num, zero = true, start = 0, unit = "") { 39 | let res = []; 40 | for (let i = start; i < num; i++) { 41 | let obj = { 42 | label: zero ? ('00' + i).slice(-2) : i + unit, 43 | value: zero ? ('00' + i).slice(-2) : i + unit, 44 | }; 45 | res.push(obj) 46 | } 47 | return res || [] 48 | } 49 | 50 | /** 51 | * 获取年份下拉 52 | * @returns 53 | */ 54 | export function toYearStr() { 55 | let res = []; 56 | for (let i = 2018; i < 2048; i++) { 57 | let obj = { 58 | label: i + "年", 59 | value: i + "年", 60 | }; 61 | res.push(obj) 62 | } 63 | return res || [] 64 | } 65 | 66 | /** 67 | * 复制功能 68 | * @param {String} text 被复制的文本 69 | */ 70 | export function copyText(text) { 71 | var textarea = document.createElement('textarea'); 72 | textarea.value = text; 73 | document.body.appendChild(textarea); 74 | textarea.select(); 75 | document.execCommand('copy'); 76 | document.body.removeChild(textarea); 77 | } 78 | 79 | /** 80 | * 获得的文本转换为文本+表情包的 v-html 81 | * @param {String} text 文本 82 | */ 83 | export function renderText(text, emojiBase64) { 84 | let replacedText = text.replace(/\[.*?\]/g, (match) => { 85 | const emoticon = match.trim().replace('[', '').replace(']', ''); 86 | if (emojiBase64.hasOwnProperty(emoticon)) { 87 | const imageUrl = emojiBase64[emoticon]; 88 | return `${emoticon}`; 89 | } 90 | return match; 91 | }).replace(/\n/g, "
"); 92 | 93 | return replacedText; 94 | } 95 | 96 | /** 97 | * 通过value返回arr数组的label 98 | * @param {Array} arr 99 | * @param {Number/String} value 100 | * @returns 101 | */ 102 | export function filterLabel(arr, value) { 103 | if (!arr.length) { 104 | return "" 105 | } 106 | return arr.find(item => item["value"] === value)["label"] 107 | } 108 | 109 | /** 110 | * 延时函数 111 | * @param {Number} time 112 | * @returns 113 | */ 114 | export const sleep = async(time) => { 115 | return new Promise((resolve, reject) => { 116 | setTimeout(() => { 117 | resolve() 118 | }, time) 119 | }); 120 | } 121 | 122 | /** 123 | * 保留前面和后面各 6 位字符,并用省略号替代中间部分 124 | * @param {*} str 原字符串 125 | * @param {*} maxLength 文本允许最大长度 126 | * @returns 127 | */ 128 | export const truncateMiddle = (str, maxLength) => { 129 | if (str.length <= maxLength) { 130 | return str; 131 | } 132 | 133 | const ellipsis = '...'; 134 | const startLength = Math.ceil((maxLength - ellipsis.length) / 2); 135 | const endLength = Math.floor((maxLength - ellipsis.length) / 2); 136 | 137 | const truncatedStr = str.substr(0, startLength) + ellipsis + str.substr(str.length - endLength); 138 | return truncatedStr; 139 | } -------------------------------------------------------------------------------- /vite.config.js: -------------------------------------------------------------------------------- 1 | import { defineConfig, loadEnv } from "vite"; 2 | import vue from '@vitejs/plugin-vue' 3 | import { resolve } from "path"; 4 | 5 | // https://vitejs.dev/config/ 6 | export default defineConfig(({ mode }) => { 7 | const { VITE_BASE_PATH } = loadEnv(mode, process.cwd()); 8 | return { 9 | plugins: [vue()], 10 | resolve: { 11 | // ↓路径别名,主要是这部分 12 | alias: { 13 | "@": resolve(__dirname, "./src"), 14 | }, 15 | }, 16 | base: VITE_BASE_PATH, 17 | server: { 18 | host: "localhost", 19 | open: true, 20 | port: 9527, 21 | }, 22 | build: { 23 | chunkSizeWarningLimit: 5000, // 设置你希望的块大小警告限制,单位是字节 24 | }, 25 | }; 26 | }); --------------------------------------------------------------------------------