#53 喵星文化与宣传部发来贺电

 #51 消息列表增加右击菜单,追加删除列表的选项。置顶开关移入此处
 好友列表搜索支持拼音搜索
 群成员列表增加搜索(搜群名片和 QQ 昵称都可以)
 #51 支持好友分组
 新增依赖 vue3-bcui、pinyin
🐛 文件预览存在 https 跨域问题
🐛 msgView 初始错误
 现在 BCUI 依赖改为本地而不依靠 github
⬆️ 更新依赖 vue3-bcui => 0.2.1
🌐 重制喵语
💚[build-electron]
This commit is contained in:
林小槐 2023-04-27 14:18:19 +08:00 committed by GitHub
commit d7155f312d
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
26 changed files with 1958 additions and 427 deletions

View File

@ -1,6 +1,6 @@
{
"name": "stapxs-qq-lite",
"version": "2.4.3",
"version": "2.5.0",
"private": false,
"author": "Stapx Steve [林槐]",
"description": "一个兼容 oicq-http 的非官方网页版 QQ 客户端,使用 Vue 重制的全新版本。",
@ -28,6 +28,7 @@
"jquery": "^3.6.0",
"js-file-downloader": "^1.1.24",
"layui": "^2.8.0-beta.2",
"pinyin": "^3.0.0-alpha.4",
"raw-loader": "^4.0.2",
"register-service-worker": "^1.7.2",
"semver-compare": "^1.0.0",
@ -42,6 +43,7 @@
"vue-gtag-next": "^1.14.0",
"vue-i18n": "^9.2.2",
"vue-infinite-scroll": "^2.0.2",
"vue3-bcui": "^0.2.1",
"vue3-infinite-scroll-better": "^2.2.0",
"xss": "^1.0.14"
},

View File

@ -0,0 +1,201 @@
Apache License
Version 2.0, January 2004
http://www.apache.org/licenses/
TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION
1. Definitions.
"License" shall mean the terms and conditions for use, reproduction,
and distribution as defined by Sections 1 through 9 of this document.
"Licensor" shall mean the copyright owner or entity authorized by
the copyright owner that is granting the License.
"Legal Entity" shall mean the union of the acting entity and all
other entities that control, are controlled by, or are under common
control with that entity. For the purposes of this definition,
"control" means (i) the power, direct or indirect, to cause the
direction or management of such entity, whether by contract or
otherwise, or (ii) ownership of fifty percent (50%) or more of the
outstanding shares, or (iii) beneficial ownership of such entity.
"You" (or "Your") shall mean an individual or Legal Entity
exercising permissions granted by this License.
"Source" form shall mean the preferred form for making modifications,
including but not limited to software source code, documentation
source, and configuration files.
"Object" form shall mean any form resulting from mechanical
transformation or translation of a Source form, including but
not limited to compiled object code, generated documentation,
and conversions to other media types.
"Work" shall mean the work of authorship, whether in Source or
Object form, made available under the License, as indicated by a
copyright notice that is included in or attached to the work
(an example is provided in the Appendix below).
"Derivative Works" shall mean any work, whether in Source or Object
form, that is based on (or derived from) the Work and for which the
editorial revisions, annotations, elaborations, or other modifications
represent, as a whole, an original work of authorship. For the purposes
of this License, Derivative Works shall not include works that remain
separable from, or merely link (or bind by name) to the interfaces of,
the Work and Derivative Works thereof.
"Contribution" shall mean any work of authorship, including
the original version of the Work and any modifications or additions
to that Work or Derivative Works thereof, that is intentionally
submitted to Licensor for inclusion in the Work by the copyright owner
or by an individual or Legal Entity authorized to submit on behalf of
the copyright owner. For the purposes of this definition, "submitted"
means any form of electronic, verbal, or written communication sent
to the Licensor or its representatives, including but not limited to
communication on electronic mailing lists, source code control systems,
and issue tracking systems that are managed by, or on behalf of, the
Licensor for the purpose of discussing and improving the Work, but
excluding communication that is conspicuously marked or otherwise
designated in writing by the copyright owner as "Not a Contribution."
"Contributor" shall mean Licensor and any individual or Legal Entity
on behalf of whom a Contribution has been received by Licensor and
subsequently incorporated within the Work.
2. Grant of Copyright License. Subject to the terms and conditions of
this License, each Contributor hereby grants to You a perpetual,
worldwide, non-exclusive, no-charge, royalty-free, irrevocable
copyright license to reproduce, prepare Derivative Works of,
publicly display, publicly perform, sublicense, and distribute the
Work and such Derivative Works in Source or Object form.
3. Grant of Patent License. Subject to the terms and conditions of
this License, each Contributor hereby grants to You a perpetual,
worldwide, non-exclusive, no-charge, royalty-free, irrevocable
(except as stated in this section) patent license to make, have made,
use, offer to sell, sell, import, and otherwise transfer the Work,
where such license applies only to those patent claims licensable
by such Contributor that are necessarily infringed by their
Contribution(s) alone or by combination of their Contribution(s)
with the Work to which such Contribution(s) was submitted. If You
institute patent litigation against any entity (including a
cross-claim or counterclaim in a lawsuit) alleging that the Work
or a Contribution incorporated within the Work constitutes direct
or contributory patent infringement, then any patent licenses
granted to You under this License for that Work shall terminate
as of the date such litigation is filed.
4. Redistribution. You may reproduce and distribute copies of the
Work or Derivative Works thereof in any medium, with or without
modifications, and in Source or Object form, provided that You
meet the following conditions:
(a) You must give any other recipients of the Work or
Derivative Works a copy of this License; and
(b) You must cause any modified files to carry prominent notices
stating that You changed the files; and
(c) You must retain, in the Source form of any Derivative Works
that You distribute, all copyright, patent, trademark, and
attribution notices from the Source form of the Work,
excluding those notices that do not pertain to any part of
the Derivative Works; and
(d) If the Work includes a "NOTICE" text file as part of its
distribution, then any Derivative Works that You distribute must
include a readable copy of the attribution notices contained
within such NOTICE file, excluding those notices that do not
pertain to any part of the Derivative Works, in at least one
of the following places: within a NOTICE text file distributed
as part of the Derivative Works; within the Source form or
documentation, if provided along with the Derivative Works; or,
within a display generated by the Derivative Works, if and
wherever such third-party notices normally appear. The contents
of the NOTICE file are for informational purposes only and
do not modify the License. You may add Your own attribution
notices within Derivative Works that You distribute, alongside
or as an addendum to the NOTICE text from the Work, provided
that such additional attribution notices cannot be construed
as modifying the License.
You may add Your own copyright statement to Your modifications and
may provide additional or different license terms and conditions
for use, reproduction, or distribution of Your modifications, or
for any such Derivative Works as a whole, provided Your use,
reproduction, and distribution of the Work otherwise complies with
the conditions stated in this License.
5. Submission of Contributions. Unless You explicitly state otherwise,
any Contribution intentionally submitted for inclusion in the Work
by You to the Licensor shall be under the terms and conditions of
this License, without any additional terms or conditions.
Notwithstanding the above, nothing herein shall supersede or modify
the terms of any separate license agreement you may have executed
with Licensor regarding such Contributions.
6. Trademarks. This License does not grant permission to use the trade
names, trademarks, service marks, or product names of the Licensor,
except as required for reasonable and customary use in describing the
origin of the Work and reproducing the content of the NOTICE file.
7. Disclaimer of Warranty. Unless required by applicable law or
agreed to in writing, Licensor provides the Work (and each
Contributor provides its Contributions) on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
implied, including, without limitation, any warranties or conditions
of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A
PARTICULAR PURPOSE. You are solely responsible for determining the
appropriateness of using or redistributing the Work and assume any
risks associated with Your exercise of permissions under this License.
8. Limitation of Liability. In no event and under no legal theory,
whether in tort (including negligence), contract, or otherwise,
unless required by applicable law (such as deliberate and grossly
negligent acts) or agreed to in writing, shall any Contributor be
liable to You for damages, including any direct, indirect, special,
incidental, or consequential damages of any character arising as a
result of this License or out of the use or inability to use the
Work (including but not limited to damages for loss of goodwill,
work stoppage, computer failure or malfunction, or any and all
other commercial damages or losses), even if such Contributor
has been advised of the possibility of such damages.
9. Accepting Warranty or Additional Liability. While redistributing
the Work or Derivative Works thereof, You may choose to offer,
and charge a fee for, acceptance of support, warranty, indemnity,
or other liability obligations and/or rights consistent with this
License. However, in accepting such obligations, You may act only
on Your own behalf and on Your sole responsibility, not on behalf
of any other Contributor, and only if You agree to indemnify,
defend, and hold each Contributor harmless for any liability
incurred by, or claims asserted against, such Contributor by reason
of your accepting any such warranty or additional liability.
END OF TERMS AND CONDITIONS
APPENDIX: How to apply the Apache License to your work.
To apply the Apache License to your work, attach the following
boilerplate notice, with the fields enclosed by brackets "[]"
replaced with your own identifying information. (Don't include
the brackets!) The text should be enclosed in the appropriate
comment syntax for the file format. We also recommend that a
file or class name and description of purpose be included on the
same "printed page" as the copyright notice for easier
identification within third-party archives.
Copyright [yyyy] [name of copyright owner]
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.

View File

@ -0,0 +1,35 @@
:root {
/* 卡片颜色 */
--color-bg: #2D2D2D;
--color-card: #3A3A3A;
--color-card-1: #494949;
--color-card-2: #5F5F5F;
--color-bg-rgb: 45, 45, 45;
--color-card-rgb: 58, 58, 58;
--color-card-1-rgb: 73, 73, 73;
--color-card-2-rgb: 95, 95, 95;
/* 字体颜色 */
--color-font: #FFFFFF;
--color-font-1: #CFCFCF;
--color-font-2: #B0B0B0;
/* 字体颜色(反转) */
--color-font-r: var(--color-bg);
--color-font-1-r: var(--color-card);
/* 阴影颜色 */
--color-shader: #1010109c;
/* 主题色 */
--color-main: #c8e5ff;
/* 内置主题色*/
--color-main-0: #c8e5ff;
--color-main-1: #d4ffcf;
--color-main-2: #ffafaa;
--color-main-3: #cdb7ff;
--color-main-4: #f9d27d;
--color-main-5: #bcbfc7;
}

View File

@ -0,0 +1,35 @@
:root {
/* 卡片颜色 */
--color-bg: #F8F9FA;
--color-card: #FFFFFF;
--color-card-1: #F1F3F5;
--color-card-2: #e3e8ec;
--color-bg-rgb: 248, 249, 250;
--color-card-rgb: 255, 255, 255;
--color-card-1-rgb: 241, 243, 245;
--color-card-2-rgb: 227, 232, 236;
/* 字体颜色 */
--color-font: #50534F;
--color-font-1: #5c5f5a;
--color-font-2: #7d817c;
/* 字体颜色(反转) */
--color-font-r: var(--color-bg);
--color-font-1-r: var(--color-card);
/* 阴影颜色 */
--color-shader: #72727240;
/* 主题色 */
--color-main: #606E7A;
/* 内置主题色*/
--color-main-0: #606E7A;
--color-main-1: #92aa8a;
--color-main-2: #f0a1a8;
--color-main-3: #8076a3;
--color-main-4: #f9a633;
--color-main-5: #50534f;
}

View File

@ -0,0 +1,468 @@
input {
caret-color: var(--color-main);
color: var(--color-font);
}
.ss-code {
background: var(--color-main);
color: var(--color-font-r);
border-radius: 7px;
padding: 3px 10px;
margin: 0 5px;
}
.ss-card {
background-color: var(--color-card);;
box-shadow:0 0 5px transparent;
transition: box-shadow .3s;
color: var(--color-font);
border-radius: 7px;
min-height: 40px;
min-width: 40px;
padding: 20px;
}
.ss-card div[class="ss-card"] {
min-height: 65px;
padding: 0;
}
.ss-card div[class="ss-card"] header {
padding: 20px 0 0 20px;
}
.ss-card div[class="ss-card"] > button > svg {
margin-right: 20px;
margin-top: -25px;
}
.ss-card:hover {
box-shadow:0 0 5px var(--color-shader);
}
.ss-card header {
color: var(--color-font);
letter-spacing: 0.1rem;
padding-bottom: 10px;
font-size: 1.02rem;
font-weight: 300;
text-indent: 0;
}
.ss-card header div:first-child {
background: var(--color-main);
margin-right: 20px;
border-radius: 5px;
height: 25px;
float: left;
width: 5px;
}
.ss-card header > i:first-child {
color: var(--color-main);
display: inline-block;
margin-right: 10px;
text-align: center;
font-size: 1.1rem;
min-width: 20px;
}
.ss-button {
background: var(--color-main);
color: var(--color-font-r);
border-radius: 7px;
font-size: 0.95rem;
font-weight: 600;
height: 33px;
border: 0;
}
.ss-button:hover {
opacity: 0.95;
}
.ss-button:focus {
outline: none;
}
.ss-button:active {
opacity: 0.9;
}
.ss-button:disabled {
opacity: 0.4;
}
.ss-input {
background: var(--color-card-1);
border-radius: 7px;
padding: 0 10px;
font-size: 15px;
height: 35px;
border: 0;
}
.ss-input:focus {
outline: 2px solid var(--color-card-1);
}
.ss-pop {
-webkit-box-shadow: 0 0 5px var(--color-shader);
-moz-box-shadow: 0 0 5px var(--color-shader);
box-shadow: 0 0 5px var(--color-shader);
background: var(--color-bg);
}
.ss-pop div[class="arrow"]:before {
border: none;
}
.ss-pop div[class="arrow"]:after {
border: none;
}
.ss-pop div {
color: var(--color-font);
}
.ss-radio {
--radio-size: 32px;
height: var(--radio-size);
margin-bottom: 0;
}
.ss-radio:hover > div:nth-child(2) {
padding: calc((var(--radio-size) / 4) + 1px);
}
.ss-radio > div:nth-child(2) {
padding: calc((var(--radio-size) / 4) + 2px);
border-radius: var(--radio-size);
background: var(--color-main);
height: var(--radio-size);
width: var(--radio-size);
transition: padding .1s;
}
.ss-radio > div:nth-child(2) > div {
background: #fff;
border-radius: 100%;
width: 100%;
height: 100%;
}
.ss-radio input {
display: none;
}
.ss-radio input:checked ~ div:nth-child(2) {
padding: calc(var(--radio-size) / 4);
}
.ss-checkbox {
--checkbox-size: 13px;
margin-bottom: 0;
display: flex;
align-items: center;
}
.ss-checkbox > input {
display: none;
}
.ss-checkbox > div {
border: 1px solid var(--color-font);
border-radius: 30%;
background: transparent;
transition: background .3s, border .1s;
height: var(--checkbox-size);
width: var(--checkbox-size);
}
.ss-checkbox > input:checked ~ div {
background: var(--color-bg);
border: calc(var(--checkbox-size) / 3) solid var(--color-main);
}
.ss-checkbox > span {
margin-left: 10px;
font-size: 0.9rem;
}
.ss-checkbox.button {
border: 2px solid var(--color-main);
border-radius: 7px;
background: transparent;
padding: 10px 15px;
}
.ss-checkbox.button > div {
border: 0 !important;
max-width: 5px;
border-radius: 5px;
transform: scaleY(0);
background: var(--color-main) !important;
transition: transform .3s;
}
.ss-checkbox.button > input:checked ~ div {
transform: scaleY(1);
}
.ss-switch {
--switch-dot-border: 4px;
--switch-dot-margin: 5px;
--switch-height: 30px;
min-width: 55px;
margin-bottom: 0;
}
.ss-switch > div {
border-radius: var(--switch-height);
background: var(--color-card-1);
height: var(--switch-height);
transition: background .4s;
width: 100%;
}
.ss-switch > div > div {
transition: margin-left .3s cubic-bezier(0.85, 0, 0.12, 0.99), border .2s;
border-radius: calc(var(--switch-height) - (var(--switch-dot-margin) * 2));
height: calc(var(--switch-height) - (var(--switch-dot-margin) * 2));
width: calc(var(--switch-height) - (var(--switch-dot-margin) * 2));
border: var(--switch-dot-border) solid #fff;
box-shadow:0 0 5px var(--color-shader);
margin-left: var(--switch-dot-margin);
margin-top: var(--switch-dot-margin);
background: var(--color-main);
float: left;
}
.ss-switch input {
display: none;
}
.ss-switch input:checked ~ div {
background: var(--color-main);
}
.ss-switch input:checked ~ div > div {
border: calc((var(--switch-height) - var(--switch-dot-margin) * 2) / 2 + 0.5px) solid #fff;
margin-left: calc(100% - var(--switch-height) + var(--switch-dot-margin));
}
.ss-code-input {
flex-direction: initial;
justify-content: center;
padding-top: 30px;
display: flex;
}
.ss-code-input input {
background: var(--color-card-1);
outline: 2px solid transparent;
caret-color: transparent;
transition: outline .3s;
border-radius: 7px;
text-align: center;
font-size: 1.5rem;
margin: 0 10px;
height: 60px;
width: 60px;
border: 0;
}
.ss-code-input input:first-child {
padding: 0;
margin: 0;
height: 0;
width: 0;
}
.ss-code-input-selete {
outline: 2px solid var(--color-main) !important;
}
.ss-code-input-err {
outline: 2px solid #ef5f5f !important;
}
.ana-card {
color: var(--color-font);
text-align: center;
font-size: 0.9rem;
font-weight: 100;
display: flex;
height: 60px;
}
.ana-card div {
background: var(--color-main);
border-radius: 5px;
height: 100%;
width: 5px;
}
.ana-card span {
width: 100%;
}
.ana-card-left {
text-align: left;
}
footer > div:first-child {
color: var(--color-font);
margin-bottom: 20px;
}
footer > div:first-child > span {
margin-left: 20px;
font-size: 0.7rem;
}
footer > div:last-child {
margin-bottom: 10px;
text-align: center;
margin-top: -10px;
font-size: 0.7rem;
}
footer > div:last-child span a {
color: var(--color-font-1);
}
footer header {
color: var(--color-main);
}
footer header span {
color: var(--color-font-1);
font-size: 0.7rem;
margin-left: 10px;
}
.cls-1 {
fill: var(--color-card-1);
}
.bar-search {
border: 0;
height: 35px;
font-size: 15px;
margin-right: 0 !important;
background: var(--color-card-1);
}
.bar-search:focus {
background: var(--color-card-1);
outline: none;
-webkit-box-shadow:0 0 5px var(--color-shader);
-moz-box-shadow:0 0 5px var(--color-shader);
box-shadow:0 0 5px var(--color-shader);
}
.avatar {
cursor: hand;
overflow: hidden;
margin-left: 20px;
--main-size: 33px;
margin-right: 5px;
width: var(--main-size);
height: var(--main-size);
border-radius: var(--main-size);
background: var(--color-card-1);
}
.avatar img {
width: var(--main-size);
height: var(--main-size);
}
.user-name {
display: none;
}
.scroll-top {
border-top: 1px dashed var(--color-main);
margin: 0 30px;
}
pre {
background: transparent !important;
overflow: visible !important;
padding: 0 !important;
}
pre:before {
display: none !important;
}
pre:after {
display: none !important;
}
pre > code {
font-family: 'Fira Code', monospace !important;
padding: 1rem !important;
}
@supports (font-variation-settings: normal) {
pre > code
{
font-family: 'Fira Code VF', monospace !important;
}
}
pre > code span {
background: transparent !important;
}
pre[class*=language-]>code {
border-left: 0px solid var(--color-main) !important;
background-color: var(--color-card-2) !important;
background-image: none !important;
border-left: 10px solid #358ccb;
background-origin: content-box;
background-attachment: local;
box-shadow: none !important;
background-size: 3em 3em;
margin-bottom: -75px;
border-radius: 7px;
position: relative;
margin-top: -10px;
z-index: 1;
}
code[class*=language-] {
max-height: inherit;
font-size: 0.8rem;
height: inherit;
padding: 0 1em;
display: block;
overflow: auto;
}
.about-text {
padding: 20px;
}
.about-text i {
color: var(--color-font-1);
margin-bottom: 10px;
font-style: normal;
font-size: 0.9rem;
font-weight: 400;
text-indent: 2em;
display: block;
}
.about-text a {
color: var(--color-font);
font-weight: bold;
}
.no-indent i {
text-indent: 0;
}
::-webkit-scrollbar-thumb {
background: var(--color-main);
border-radius: 6px;
}
::-webkit-scrollbar {
background-color:var(--color-card-1);
width:6px;
}
::-webkit-scrollbar-button {
display: none;
}
@media screen and (max-width: 992px) {
.avatar {
width: auto;
height: auto;
margin-left: 0;
border-radius: 0;
background: none;
}
.avatar img {
display: none;
}
.bar-search {
display: none !important;
}
.user-name {
display: unset;
cursor: pointer;
color: var(--color-font-1);
}
.user-name:hover {
color: var(--color-font);
opacity: 0.7;
}
}
.navbar-dark .navbar-brand {
color: var(--color-font) !important;
}
.navbar-dark .navbar-nav .nav-link.active {
color: var(--color-font) !important;
}
.navbar-dark .navbar-nav .nav-link {
color: var(--color-font-1) !important;
}
.navbar-dark:hover .navbar-nav:hover .nav-link:hover {
color: var(--color-font) !important;
opacity: 0.7 !important;
}

View File

@ -0,0 +1,25 @@
// 自动暗黑模式相关代码
let media = window.matchMedia('(prefers-color-scheme: dark)');
if(is_auto_dark !== false) {
if (media.matches) {
changeColor("dark")
} else {
changeColor("light")
}
}
let callback = (e) => {
if(is_auto_dark) {
console.log("正在自动切换颜色 ……")
let prefersDarkMode = e.matches;
if (prefersDarkMode) {
changeColor("dark")
} else {
changeColor("light")
}
}
};
if (typeof media.addEventListener === 'function') {
media.addEventListener('change', callback);
} else if (typeof media.addListener === 'function') {
media.addListener(callback);
}

View File

@ -0,0 +1,193 @@
let fist_load = true
function changeColor(type) {
if(!fist_load) {
// 启用颜色渐变动画
document.body.style.transition = 'background, color, background-color .3s'
} else {
fist_load = false
}
// 切换颜色
let match_list = ['color-.*\.css', 'prism-.*\.css']
const css_list = document.getElementsByTagName("link")
for(let i=0; i<css_list.length; i++) {
name = css_list[i].href
match_list.forEach(function (value) {
if(name.match(value) != null) {
const newLink = document.createElement("link");
newLink.setAttribute("rel", "stylesheet");
newLink.setAttribute("type", "text/css");
if(type === "dark") {
newLink.setAttribute("href", name.replace('light', 'dark'));
} else {
newLink.setAttribute("href", name.replace('dark', 'light'));
}
document.getElementsByTagName("head").item(0).replaceChild(newLink, css_list[i]);
}
})
}
}
function foldChange(sender) {
const svg = sender.getElementsByTagName('svg');
if(svg[0].style.transform === 'rotate(-90deg)') {
svg[0].style.transform = 'rotate(90deg)'
animateScroll(sender, 40)
} else {
svg[0].style.transform = 'rotate(-90deg)'
}
}
function animateScroll(element, speed) {
let rect=element.getBoundingClientRect()
let top=window.pageYOffset+rect.top
let currentTop=document.documentElement.scrollTop
let requestId
function step(timestamp) {
currentTop+=speed
if(currentTop<=top){
window.scrollTo(0,currentTop)
requestId=window.requestAnimationFrame(step)
}else{
window.cancelAnimationFrame(requestId)
}
}
window.requestAnimationFrame(step)
}
function scrollDiv(sender) {
const par_body = sender.parentNode
const line = par_body.getElementsByClassName('scroll-top')[0];
if(sender.scrollTop === 0) {
line.style.display = 'none'
} else {
line.style.display = 'block'
}
}
function getQueryVariable(variable) {
const query = window.location.search.substring(1);
const vars = query.split("&");
for (let i=0; i<vars.length; i++) {
const pair = vars[i].split("=");
if(pair[0] === variable){
return pair[1]
}
}
return false
}
function initCodeInput(body, fun, regex) {
// 初始化输入框
if(body.classList.toString().indexOf('ss-code-input') >= 0) {
// 初始化 label onclick 事件
body.onclick = function () { codeInputAllow(body) }
// 初始化主输入框
const input = body.getElementsByTagName('input')[0]
input.oninput = function() { codeInputChanged(body, fun, regex) }
input.onblur = function() { codeInputNoAllow(body) }
input.dataset.typeing = "false"
input.addEventListener('compositionstart',function(e){ input.dataset.typeing = "true" }, false)
input.addEventListener('compositionend',function(e){ input.dataset.typeing = "false"; }, false)
if(input !== undefined) {
// 添加显示输入框
for(var i=0; i<body.dataset.num; i++) {
// 构建
let inputShow = document.createElement("input")
inputShow.onclick = function () { codeInputAllow(body) }
inputShow.dataset.id = (i+1).toString()
inputShow.disabled = true
// 添加
body.appendChild(inputShow)
}
}
}
}
function codeInputAllow(body) {
// 输入框 label 点击事件
const inputs = body.getElementsByTagName('input')
inputs[0].focus()
codeInputChanged(body)
}
function codeInputNoAllow(body) {
const inputs = body.getElementsByTagName('input')
for(let i=1; i<inputs.length; i++) {
inputs[i].classList = ""
}
}
function codeInputChanged(body, fun, regex) {
// 主输入框变化事件
const inputs = body.getElementsByTagName('input')
if(inputs !== undefined && inputs.length > 1 && inputs[0].dataset.typeing === "false") {
if(regex === undefined) {
regex = ""
}
if(inputs[0].dataset.up === "true") {
inputs[0].value = inputs[0].value.toUpperCase()
}
// 变更输入框内容
for(let i=1; i<inputs.length; i++) {
inputs[i].value = ""
}
for(let i=0; i<inputs[0].value.length; i++) {
// 检查正则表达式
const reg = new RegExp(regex)
if(reg.test(inputs[0].value.substring(i, i+1))) {
if(i < inputs.length - 2) {
inputs[i+1].classList = ""
inputs[i+1].value = inputs[0].value.substring(i, i+1)
if(i + 2 < inputs.length) {
inputs[i+2].classList = "ss-code-input-selete"
}
if(i + 3 < inputs.length) {
inputs[i+3].classList = ""
}
} else if( i == inputs.length - 2) {
inputs[i+1].value = inputs[0].value.substring(i, i+1)
if(fun !== undefined) {
// 触发函数
inputs[0].disabled = true
// 完成部分动画
setTimeout(() => {
fun()
}, 300)
}
}
} else {
inputs[0].value = inputs[0].value.substring(0, inputs[0].value.length - 1)
inputs[i+1].classList = "ss-code-input-selete ss-code-input-err"
setTimeout(() => {
inputs[i+1].classList = "ss-code-input-selete"
}, 500)
}
}
if(inputs[0].value.length == 0) {
inputs[1].classList = "ss-code-input-selete"
inputs[2].classList = ""
}
// 防止光标不在最后
inputs[0].setSelectionRange(inputs[0].value.length, inputs[0].value.length)
}
}
function getCodeInput(body) {
if(body.classList.toString().indexOf('ss-code-input') >= 0) {
const inputs = body.getElementsByTagName('input')
return inputs[0].value.substring(0, inputs.length - 1)
}
}
function cleanCodeInput(body) {
if(body.classList.toString().indexOf('ss-code-input') >= 0) {
const inputs = body.getElementsByTagName('input')
inputs[0].value = ""
inputs[0].disabled = false
for(let i=1; i<inputs.length; i++) {
inputs[i].classList = ""
}
codeInputChanged(body)
}
}

View File

@ -7,8 +7,8 @@
<meta name="referrer" content="no-referrer" id="referrer">
<link rel="icon" href="<%= BASE_URL %>favicon.ico">
<title>Stapxs QQ Lite</title>
<link rel="stylesheet" href="https://stapxs.github.io/Border-Card-UI/css/style.css">
<link rel="stylesheet" href="https://stapxs.github.io/Border-Card-UI/css/color-light.css">
<link rel="stylesheet" href="Border-Card-UI/css/style.css">
<link rel="stylesheet" href="Border-Card-UI/css/color-light.css">
</head>
<body>
<noscript>
@ -16,5 +16,5 @@
</noscript>
<div id="app"></div>
</body>
<script src="https://stapxs.github.io/Border-Card-UI/js/main.js"></script>
<script src="Border-Card-UI/js/main.js"></script>
</html>

View File

@ -301,6 +301,7 @@ textarea {
.msg-menu {
position: absolute;
overflow: hidden;
height: 100%;
width: 100%;
z-index: 10;

View File

@ -362,7 +362,7 @@ html, body {
flex: 1;
}
.friend-list > div:last-child {
width: calc(100% - 5px);
width: calc(100% - 10px);
padding: 0 7px 0 5px;
-webkit-box-flex: 1;
overflow-y: scroll;
@ -391,6 +391,7 @@ html, body {
background: var(--color-main);
color: var(--color-font-r);
}
.friend-body.onmenu,
.friend-body:hover {
background: var(--color-card-2) !important;
}
@ -483,7 +484,7 @@ html, body {
}
/* TODO: BCUI - 这段 css 将在将来迁移到 Border Card UI 中合并 */
.menu {
.msg-menu-body {
background: rgba(var(--color-bg-rgb), 0.7);
box-shadow: 0 0 5px var(--color-shader);
backdrop-filter: blur(50px);
@ -497,13 +498,13 @@ html, body {
padding: 10px;
width: 20%;
}
.menu.topOut {
.msg-menu-body.topOut {
transition: transform .1s, margin-top .1s;
}
.menu.show {
.msg-menu-body.show {
transform: scaleY(1);
}
.menu > div {
.msg-menu-body > div {
transition: background .3s;
background: transparent;
align-items: center;
@ -512,10 +513,10 @@ html, body {
cursor: pointer;
display: flex;
}
.menu > div:hover {
.msg-menu-body > div:hover {
background: var(--color-main);
}
.menu > div > div > svg {
.msg-menu-body > div > div > svg {
fill: var(--color-font-1);
transition: fill .3s;
margin-right: 10px;
@ -523,17 +524,17 @@ html, body {
height: 1rem;
width: 1rem;
}
.menu > div:hover > div > svg {
.msg-menu-body > div:hover > div > svg {
fill: var(--color-font-r);
}
.menu > div > a {
.msg-menu-body > div > a {
color: var(--color-font);
text-overflow: ellipsis;
transition: color .3s;
white-space: nowrap;
overflow: hidden;
}
.menu > div:hover > a {
.msg-menu-body > div:hover > a {
color: var(--color-font-r);
}
@ -1065,6 +1066,7 @@ html, body {
opacity: 1;
}
.friend-list > div:first-child label {
border-radius:7px;
display: none;
}
.friend-list > div:last-child.open > div {
@ -1117,10 +1119,10 @@ html, body {
max-width: calc(100% - 80px);
}
/* 右击菜单 */
.menu {
.msg-menu-body {
width: 30%;
}
.menu > div {
.msg-menu-body > div {
padding: 5px 15px;
}
}

View File

@ -295,5 +295,10 @@
"pop_friend_added": "Successfully added {name} as friend!",
"option_view_no_window_mac_style": "macOS-inspired title bar",
"option_view_no_window_mac_style_tip": "Check out the style in any OS!",
"chat_temp_from": "From group: {group}"
"chat_temp_from": "From group: {group}",
"list_menu_top": "Pin",
"list_menu_canceltop": "Unpin",
"list_menu_remove": "Delete",
"list_menu_readed": "Mark as read",
"friend_group": "Group"
}

View File

@ -1,221 +1,295 @@
{
"author": "Stapx Steve [林槐]",
"base_exit": "退出",
"base_search": "寻找小鱼干 ……",
"botinfo_app_full_name": "后端全称",
"botinfo_coolq_directory": "运行目录",
"botinfo_coolq_version": "版本",
"botinfo_go-cqhttp": "go-cqhttp",
"botinfo_http_api": "HTTP API 版本",
"botinfo_lost_pkt_cnt": "丢失包数量",
"botinfo_lost_times": "掉线次数",
"botinfo_msg_cnt_per_min": "每分钟消息",
"botinfo_plugin_build_configuration": "构建类型",
"botinfo_plugin_build_number": "构建版本号",
"botinfo_recv_msg_cnt": "接收消息数量",
"botinfo_recv_pkt_cnt": "接收包总数",
"botinfo_remote_ip": "QQ 服务器地址",
"botinfo_remote_port": "QQ 服务器端口",
"botinfo_sent_msg_cnt": "发送消息数量",
"botinfo_sent_pkt_cnt": "发送包数量",
"botinfo_start_time": "启动时间",
"botinfo_stat": "状态信息",
"chat_chat_info_district": "地区",
"chat_chat_info_birthday": "生日",
"chat_chat_info_chinese_zodiac": "鼠&牛&虎&兔&龙&蛇&马&羊&猴&鸡&狗&猪",
"chat_chat_info_config": "设置",
"chat_chat_info_dead_day": "天后",
"chat_chat_info_file": "文件",
"chat_chat_info_file_num": "共 {num} 个文件",
"chat_chat_info_group": "喵圈资料",
"chat_chat_info_introduction": "喵喵",
"chat_chat_info_is_admin": "你是管理猫",
"chat_chat_info_is_owner": "你是主子",
"chat_chat_info_lnick": "爪印",
"chat_chat_info_member": "猫成员",
"chat_chat_info_nointroduction": "主子很懒,还没有喵圈介绍哦~",
"chat_chat_info_nolnick": "爪印",
"chat_chat_info_other": "其他信息",
"chat_chat_info_user": "猫友",
"chat_face_pan_none": "没有鱼干|PS这儿的空间比较小请尽量使用更短的句子或者是词。PSS你不用在翻译中保留竖线以及以后的部分除非你认为有人会参考你的翻译翻译 XD",
"chat_fun_menu_face": "表情",
"chat_fun_menu_pic": "图片",
"chat_group_pic": "群图片",
"chat_join_time": "{time} 加入喵圈",
"chat_last_msg": "上次喵喵 - {time}",
"chat_member_type_admin": "管理猫",
"chat_member_type_owner": "主子",
"chat_merge_msg": "合并喵喵",
"chat_msg_menu_copy": "复制",
"chat_msg_menu_copy_selected": "复制选中文本",
"chat_msg_menu_forward": "转发",
"chat_msg_menu_multiple_choice": "多选",
"chat_msg_menu_reply": "回复",
"chat_msg_menu_withdraw": "撤回",
"chat_no_more_msg": "没有更多喵喵了",
"chat_no_msg": "暂无喵喵",
"chat_send": "发送",
"chat_send_pic_title": "发送图片",
"chat_space": "选择联系猫开始聊天",
"chat_unsupported_msg": "不支持的喵喵",
"chat_view_pic": "预览图片",
"description": "一个兼容 oicq-http 的非官方网页版 QQ 客户端",
"friend_title": "联系猫",
"home_card_address": "连接地址",
"home_card_auto_con": "自动连接",
"home_card_connect": "连接",
"home_card_how_to_connect": "如何连接",
"home_card_key": "连接密钥",
"home_card_save_pwd": "记住密码",
"home_card_title": "连接到 OICQ HTTP",
"home_title": "主页",
"l10n_author": "Stapx Steve",
"l10n_description": "喵喵!欢迎来到喵圈,这是喵圈的专用语言!",
"l10n_name": "中文(喵语)",
"l10n_version": "2.1.9",
"log_con_fail": "连接失败",
"log_con_success": "连接成功",
"log_revoke_miss": "没有找到这条被抢回去的喵喵 ……",
"log_we_log_all": "当前处于 all 日志模式。连接器将输出全部收发消息 ……",
"log_welcome": "欢迎使用 Stapxs QQ Lite",
"log_ws_log_debug": "当前处于 debug 日志模式。连接器将仅输出发出的消息 ……",
"name": "Stapxs QQ Lite",
"option_account_bot": "后端信息",
"option_account_bot_tip": "这是你连接的 QQ Bot 的相关信息",
"option_account_config": "喵号设置",
"option_bar_account": "喵号",
"option_bar_dev": "高级",
"option_bar_function": "功能",
"option_bar_view": "界面",
"option_dev_appmsg": "应用消息测试",
"option_dev_appmsg_tip": "#$&*#$= ……",
"option_dev_chat_nd": "消息防撤回",
"option_dev_chat_nd_tip": "说出去的话就像借出去的鱼干 ……",
"option_dev_chat_nd_tip_1": "说了不做这功能就是不做喵 ",
"option_dev_chat_pic_pan": "禁用图片发送框",
"option_dev_chat_pic_pan_tip": "你也向往自由吗?",
"option_dev_chatview": "组件选项",
"option_dev_chatview_name": "指定组件",
"option_dev_chatview_name_tip": "Game Center!",
"option_dev_chatview_tip": "这儿是关于页面可拆装组件相关的高级选项。",
"option_dev_connect": "兼容选项",
"option_dev_connect_beat": "发送心跳包",
"option_dev_connect_beat_tip": "没救了,分鱼干吧",
"option_dev_connect_tip": "这儿是关于 bot 兼容性相关的高级选项,包括一些 bot 的附加功能等。",
"option_dev_connect_type": "启用兼容",
"option_dev_connect_type_tip": "换个小鱼干会不会更好吃呢 ……",
"option_dev_debug_msg": "禁用消息渲染",
"option_dev_debug_msg_tip": "人类的语言真难学",
"option_dev_dev": "开发猫选项",
"option_dev_log_level": "日志等级",
"option_dev_log_level_all": "全部",
"option_dev_log_level_debug": "调试",
"option_dev_log_level_err": "错误",
"option_dev_log_level_info": "基本",
"option_dev_log_level_tip": "ReferenceError: fish is not defined",
"option_dev_msg_menu": "禁用自定义右击菜单",
"option_dev_msg_menu_tip": "小猫咪能有什么坏心思呢 ——",
"option_dev_notice_all": "通知所有新喵喵",
"option_dev_notice_all_tip": "喵喵喵喵喵喵喵喵喵喵!",
"option_dev_notice_close": "禁用通知",
"option_dev_notice_close_tip": "小猫咪只想睡觉!睡一整天!",
"option_dev_send_reget": "停止消息回调",
"option_dev_send_reget_tip": "不再主动获取自己的消息",
"option_dev_test": "调试",
"option_dev_ws_send": "发送原始消息",
"option_dev_ws_send_tip": "咻 ——",
"option_fun_chat": "聊天选项",
"option_fun_ga": "分析信息",
"option_fun_ga_bot": "后端类型分析",
"option_fun_ga_bot_tip": "在连接后上传所使用的 bot 的类型分析",
"option_fun_ga_tip": "我们使用谷歌分析对应用的使用情况进行分析,所有分析信息不会包含精确到用户的信息,仅用于进行使用情况分析。你可以在这儿控制分析功能的开关和额外分析项。",
"option_fun_ga_turn": "关闭分析",
"option_fun_ga_turn_tip": "真的不让看吗(小声",
"option_fun_ga_user": "定向分析",
"option_fun_ga_user_tip": "使用随机编号更加准确地进行信息分析",
"option_fun_notice": "通知选项",
"option_info_visit_github": "访问 GitHub 仓库",
"option_title": "设置",
"option_view_auto_dark": "自动深色模式",
"option_view_auto_dark_tip": "是喵的主场!",
"option_view_dark_mode": "深色模式",
"option_view_dark_mode_tip": "盯 ——",
"option_view_l10n": "喵星化",
"option_view_l10n_expired": "需要更新",
"option_view_language": "喵语Language",
"option_view_language_tip": "喵喵喵喵?",
"option_view_theme": "衣服与毛色",
"option_view_theme_color": "毛色",
"option_view_theme_color_tip": "换个心情 🎵 ~",
"version_updated": "版本已更新",
"option_dev_runtime": "输出运行时",
"option_dev_runtime_tip": "全都吐出来!",
"option_dev_runtime_run": "执行",
"chat_notice_recall": "抢回去了一条消息",
"chat_xml_unsupport": "不支持显示的 XML 消息",
"chat_link_view_success": "获取链接预览成功",
"chat_link_view_fail": "获取链接预览失败",
"chat_chat_info_bulletin_readed": "已读",
"chat_chat_info_bulletin_noread": "未读",
"chat_chat_info_bulletin_read": "{readNum} 只猫已读 | {isRead}",
"chat_chat_info_notice": "公告",
"option_dev_ui_test": "页面测试",
"option_dev_ui_test_tip": "(扒拉扒拉)",
"log_runtime": "当前启动模式为",
"log_GA_loaded": "加载谷歌分析组件完成",
"log_GA_auto_closed": "由于运行在调试模式下,谷歌分析组件并未加载 ……",
"pop_load_history_fail": "加载历史喵喵失败(构建喵喵 ID 失败)",
"pop_find_pic_fail": "定位图片失败",
"pop_log_con_fail": "连接失败",
"pop_log_con_closed": "连接关闭",
"pop_chat_forward_toooomany": "合并消息层级过多,解析失败。",
"pop_chat_chat_info_load_file_err": "加载喵圈文件失败({code}),可能是由于对象无效(冻结、解散)",
"pop_chat_load_msg_err": "加载喵喵失败({code}",
"pop_chat_send_msg_err": "发送喵喵失败({code}),可能是由于禁言或者对象无效(冻结、解散)",
"pop_chat_get_msg_err": "获取喵猫失败,正在重试",
"pop_chat_get_msg_err_fin": "获取喵喵失败",
"pop_chat_msg_not_load": "无法定位上下文",
"pop_chat_msg_menu_copy_success": "复制成功",
"pop_chat_msg_menu_copy_err": "复制喵喵失败",
"pop_chat_image_toooo_big": "图片过大",
"pop_option_dev_debug_msg_tip_1": "好 你 我 是 猫 一 只,喵喵喵",
"pop_print_all_pop": "即将输出所有应用消息5s ……",
"log_cq_msg_parsed": "解析 CQ 消息结果",
"chat_chat_info_option_top": "置顶",
"chat_chat_info_option_top_tip": "再多看我一眼(无端",
"log_com_err": "创建连接失败",
"sw_ready": "应用已通过 service worker 服务从缓存中加载,更多信息请查看 https://goo.gl/AFskqB。",
"sw_registered": "Service worker 服务注册成功。",
"sw_cached": "内容已完成缓存便于离线使用。",
"sw_update": "正在下载新的内容 ……",
"sw_updated": "新的内容已缓存完成,请刷新以生效。",
"sw_offline": "没有有效的网络连接,应用正在以离线模式运行。",
"sw_error": "注册 service worker 时发生错误",
"sw_no_internet": "没有网络",
"chat_load_img_fail": "加载图片失败",
"chat_fun_menu_jin": "精华喵喵",
"message_title": "喵喵",
"chat_fun_menu_jin_sender": "{time},由 {name} 猫设置",
"sw_need_reload": "检查到应用更新,需要重新加载 ……",
"update_history": "更新记录",
"btn_know": "知道喵",
"btn_see": "查看",
"chat_fun_at_find_emp": "没有找到匹配的猫成员",
"l10n_author_title": "作者猫:",
"option_fun_taill": "猫尾巴",
"option_fun_taill_tip": "只会追加在最后一段话后面",
"chat_show_forward": "(点击查看合并转发喵喵)",
"popbox_ohh": "好耶",
"popbox_open_times_1": "好耶Stapxs QQ Lite 已经被打开 {times} 次了!",
"popbox_open_times_2": "真的不去点个 star 喵 ……",
"btn_open_times_ok": "好喵",
"btn_open_times_no": "不要",
"popbox_tip": "提醒",
"auto_connect_tip": "连接密钥将以明文存储在浏览器 Cookie 中,请确保设备安全以防止密钥泄漏。",
"option_account_nick": "圈名",
"option_account_nick_tip": "就只是个名字而已 ……",
"option_account_lnick": "爪印",
"option_account_lnick_tip": "糊你一脸!",
"list_system_notice": "系统通知",
"sys_notice_new_friend_from": "来源:"
}
"author": "Stapx Steve [林槐]",
"base_exit": "退出",
"base_search": "寻找小鱼干 ……",
"botinfo_app_full_name": "猫堡全称",
"botinfo_coolq_directory": "猫堡地址",
"botinfo_coolq_version": "猫堡版本",
"botinfo_go-cqhttp": "go-cqhttp",
"botinfo_http_api": "HTTP API 版本",
"botinfo_lost_pkt_cnt": "丢失包数量",
"botinfo_lost_times": "掉线次数",
"botinfo_msg_cnt_per_min": "每分钟消息",
"botinfo_plugin_build_configuration": "构建类型",
"botinfo_plugin_build_number": "构建版本号",
"botinfo_recv_msg_cnt": "接收消息数量",
"botinfo_recv_pkt_cnt": "接收包总数",
"botinfo_remote_ip": "QQ 服务器地址",
"botinfo_remote_port": "QQ 服务器端口",
"botinfo_sent_msg_cnt": "发送消息数量",
"botinfo_sent_pkt_cnt": "发送包数量",
"botinfo_start_time": "启动时间",
"botinfo_stat": "状态信息",
"chat_chat_info_district": "喵星地区",
"chat_chat_info_birthday": "猫猫生日",
"chat_chat_info_chinese_zodiac": "鼠&牛&虎&猫&龙&蛇&马&羊&猴&鸡&狗&猪",
"chat_chat_info_config": "设置",
"chat_chat_info_dead_day": "猫日后",
"chat_chat_info_file": "文件",
"chat_chat_info_file_num": "共 {num} 个文件",
"chat_chat_info_group": "猫圈资料",
"chat_chat_info_introduction": "猫猫介绍",
"chat_chat_info_is_admin": "你是猫跟班",
"chat_chat_info_is_owner": "你是猫头子",
"chat_chat_info_lnick": "爪印",
"chat_chat_info_member": "猫成员",
"chat_chat_info_nointroduction": "头子很懒,还没有猫圈介绍哦~",
"chat_chat_info_nolnick": "爪印",
"chat_chat_info_other": "其他信息",
"chat_chat_info_user": "猫友",
"chat_face_pan_none": "没有鱼干 ……|PS这儿的空间比较小请尽量使用更短的句子或者是词。PSS你不用在翻译中保留竖线以及以后的部分除非你认为有人会参考你的翻译翻译 XD",
"chat_fun_menu_face": "喵脸",
"chat_fun_menu_pic": "图片",
"chat_group_pic": "猫圈图片",
"chat_join_time": "{time} 加入猫圈",
"chat_last_msg": "上次喵喵 - {time}",
"chat_member_type_admin": "猫跟班",
"chat_member_type_owner": "猫主子",
"chat_merge_msg": "合并喵喵消息",
"chat_msg_menu_copy": "揪下来",
"chat_msg_menu_copy_selected": "复制想要的文本",
"chat_msg_menu_forward": "给别人",
"chat_msg_menu_multiple_choice": "多选",
"chat_msg_menu_reply": "回复",
"chat_msg_menu_withdraw": "偷回来",
"chat_no_more_msg": "没有更多猫猫的话了",
"chat_no_msg": "暂无喵喵",
"chat_send": "发出去",
"chat_send_pic_title": "发送喵图",
"chat_space": "选择喵友开始聊天",
"chat_unsupported_msg": "不认识的喵喵",
"chat_view_pic": "预览喵图",
"description": "一个可以在喵星用的兼容 oicq-http 的非官方网页版 QQ 喵喵端",
"friend_title": "喵友",
"home_card_address": "喵堡地址",
"home_card_auto_con": "自动联络",
"home_card_connect": "联络",
"home_card_how_to_connect": "如何联络",
"home_card_key": "联络喵文",
"home_card_save_pwd": "记住喵文",
"home_card_title": "向喵堡联络",
"home_title": "喵页",
"l10n_author": "Stapx Steve [ 林槐 ]",
"l10n_description": "欢迎联络喵星!这是 Stapx QQ Lite 的喵星文化与宣传部特供中文喵语!",
"l10n_name": "中文(喵语)",
"l10n_version": "2.1.10",
"log_con_fail": "联络失败",
"log_con_success": "联络成功",
"log_revoke_miss": "没有找到这条被偷回去的喵喵 ……",
"log_we_log_all": "当前处于 all 日志模式。连接器将输出全部收发消息 ……",
"log_welcome": "欢迎使用 Stapxs QQ Lite",
"log_ws_log_debug": "当前处于 debug 日志模式。连接器将仅输出发出的消息 ……",
"name": "Stapxs QQ Lite",
"option_account_bot": "猫堡信息",
"option_account_bot_tip": "这是你联络的猫堡的相关信息",
"option_account_config": "喵号设置",
"option_bar_account": "喵号",
"option_bar_dev": "高级",
"option_bar_function": "功能",
"option_bar_view": "界面",
"option_dev_appmsg": "应用消息测试",
"option_dev_appmsg_tip": "#$&*#$= ……",
"option_dev_chat_nd": "不让别的猫偷消息",
"option_dev_chat_nd_tip": "送出去的小鱼干就像是吃掉的猫粮 ……",
"option_dev_chat_nd_tip_1": "说了不做这功能就是不做",
"option_dev_chat_pic_pan": "禁用喵图发送框",
"option_dev_chat_pic_pan_tip": "小猫咪才不用别人帮忙",
"option_dev_chatview_name": "喵话面板组件",
"option_dev_chatview_name_tip": "Game Center!",
"option_dev_connect": "别的猫堡选项",
"option_dev_connect_beat": "发送心跳包",
"option_dev_connect_beat_tip": "喵喵喵?怎么听不懂啊",
"option_dev_connect_tip": "这儿是兼容别的猫堡的高级选项,包括 bot 附加功能、热插拔组件等。",
"option_dev_debug_msg": "禁用喵喵翻译",
"option_dev_debug_msg_tip": "[喵喵喵 ……]",
"option_dev_dev": "工程猫选项",
"option_dev_log_level": "日志等级",
"option_dev_log_level_all": "全部",
"option_dev_log_level_debug": "调试",
"option_dev_log_level_err": "错误",
"option_dev_log_level_info": "基本",
"option_dev_log_level_tip": "参考错误: moYu 没有找到这个鱼干。",
"option_dev_notice_all": "通知所有新喵话",
"option_dev_notice_all_tip": "喵喵喵喵喵喵喵喵喵喵喵喵喵喵喵喵喵喵",
"option_dev_notice_close": "禁用喵叫",
"option_dev_notice_close_tip": "好嘛 …… 不烦你 ……",
"option_dev_send_reget": "停止喵话回调",
"option_dev_send_reget_tip": "不再主动获取自己的喵喵",
"option_dev_test": "工程喵工具",
"option_dev_ws_send": "发送原始喵喵",
"option_dev_ws_send_tip": "喵 ——(大声)",
"option_fun_chat": "喵话选项",
"option_fun_ga": "猫堡信息",
"option_fun_ga_bot": "猫堡类型分析",
"option_fun_ga_bot_tip": "在连接后上传所使用的 bot 的类型分析",
"option_fun_ga_tip": "我们使用谷歌分析对应用的使用情况进行分析,所有分析信息不会包含精确到用户的信息,仅用于进行使用情况分析。你可以在这儿控制分析功能的开关和额外分析项。",
"option_fun_ga_turn": "关闭分析",
"option_fun_ga_turn_tip": "真的不让看吗(小声",
"option_fun_ga_user": "定向分析",
"option_fun_ga_user_tip": "使用随机编号更加准确地进行信息分析",
"option_fun_notice": "通知选项",
"option_info_visit_github": "访问 CatHub 仓库",
"option_title": "设置",
"option_view_auto_dark": "自动夜猫子模式",
"option_view_auto_dark_tip": "盯 ————",
"option_view_dark_mode": "夜猫子模式",
"option_view_dark_mode_tip": "晚上才是喵星的白天!",
"option_view_l10n": "喵星化",
"option_view_l10n_expired": "需要更新",
"option_view_language": "喵喵Language",
"option_view_language_tip": "跪拜在崇高的喵星帝国下吧",
"option_view_theme": "毛色和挂件",
"option_view_theme_color": "喵毛颜色",
"option_view_theme_color_tip": "换个心情 🎵 ~",
"version_updated": "版本已更新",
"option_dev_runtime": "输出运行时",
"option_dev_runtime_tip": "交代你来喵星的目的!",
"option_dev_runtime_run": "执行",
"chat_notice_recall": "偷回去了一条喵话",
"chat_xml_unsupport": "不支持显示的 XML 喵话",
"chat_link_view_success": "获取链接预览成功",
"chat_link_view_fail": "获取链接预览失败",
"chat_chat_info_bulletin_readed": "已读",
"chat_chat_info_bulletin_noread": "未读",
"chat_chat_info_bulletin_read": "{readNum} 只猫已读 | {isRead}",
"chat_chat_info_notice": "猫板",
"option_dev_ui_test": "页面测试",
"option_dev_ui_test_tip": "看看肚子 ~",
"log_runtime": "当前启动模式为",
"log_GA_loaded": "加载谷歌分析组件完成",
"log_GA_auto_closed": "由于运行在调试模式下,谷歌分析组件并未加载 ……",
"pop_load_history_fail": "加载历史消息失败(构建消息 ID 失败)",
"pop_find_pic_fail": "定位喵图失败",
"pop_log_con_fail": "联络失败",
"pop_log_con_closed": "联络关闭",
"pop_chat_forward_toooomany": "合并喵话层级过多,解析失败。",
"pop_chat_chat_info_load_file_err": "加载喵圈文件失败({code}",
"pop_chat_load_msg_err": "加载喵话失败({code}",
"pop_chat_send_msg_err": "发送喵话失败({code}),可能是由于禁言或者对象无效(冻结、解散)",
"pop_chat_get_msg_err": "获取喵话失败,正在重试",
"pop_chat_get_msg_err_fin": "获取喵话失败",
"pop_chat_msg_not_load": "无法定位上下文",
"pop_chat_msg_menu_copy_success": "揪下来了",
"pop_chat_msg_menu_copy_err": "揪喵话失败",
"pop_chat_image_toooo_big": "喵图过大",
"pop_option_dev_debug_msg_tip_1": "[喵喵喵 ……]",
"pop_print_all_pop": "即将输出所有应用消息5s ……",
"log_cq_msg_parsed": "解析 CQ 消息结果",
"log_com_err": "创建联络链路失败",
"sw_ready": "应用已通过 service worker 服务从缓存中加载,更多信息请查看 https://goo.gl/AFskqB。",
"sw_registered": "Service worker 服务注册成功。",
"sw_cached": "内容已完成缓存便于离线使用。",
"sw_update": "正在下载新的内容 ……",
"sw_updated": "新的内容已缓存完成,请刷新以生效。",
"sw_offline": "没有有效的网络连接,应用正在以离线模式运行。",
"sw_error": "注册 service worker 时发生错误",
"sw_no_internet": "无法链接到猫星网络中继",
"chat_load_img_fail": "加载喵图失败",
"chat_fun_menu_jin": "精华喵话",
"message_title": "喵话",
"chat_fun_menu_jin_sender": "{time},由 {name} 猫设置",
"update_history": "工程猫记录",
"btn_know": "知道喵",
"btn_see": "查看",
"chat_fun_at_find_emp": "没有找到匹配的猫成员",
"l10n_author_title": "翻译猫:",
"option_fun_taill": "猫尾巴",
"option_fun_taill_tip": "只会追加在最后一段话后面",
"chat_show_forward": "(点击查看合并转发猫话)",
"popbox_ohh": "好喵",
"popbox_open_times_1": "喵喵Stapxs QQ Lite 已经被打开 {times} 次了!",
"popbox_open_times_2": "真的不去点个 star 给条小鱼干嘛 ……",
"btn_open_times_ok": "好喵",
"btn_open_times_no": "不喵",
"popbox_tip": "猫叫",
"auto_connect_tip": "连接喵文将以明文存储在浏览器 Cookie 中,请确保设备安全以防止喵文泄漏。",
"option_account_nick": "猫名",
"option_account_nick_tip": "就只是个名字而已 ……",
"option_account_lnick": "爪印",
"option_account_lnick_tip": "小猫咪才没有到处写字的坏心思",
"list_system_notice": "系统猫叫",
"sys_notice_new_friend_from": "来源:",
"option_dev_debug": "输出调试信息",
"option_dev_debug_tip": "到底用的什么版本呢 ……",
"btn_yes": "确定",
"option_dev_test_info": "调试信息",
"btn_next": "继续",
"option_dev_backup": "维护与备份",
"option_dev_get_backup": "导出设置项",
"option_dev_get_backup_tip": "正在向猫星中心服务器请求备份 ……",
"option_dev_set_backup": "导入设置项",
"option_dev_set_backup_tip": "上载猫猫资料将会覆盖现有数据",
"btn_no": "取消",
"import_config_fail": "导入设置项失败",
"option_dev_reset": "重置应用",
"option_dev_reset_tip": "正在注销猫星服务 ……",
"chat_jump_reply": "(查看回复的猫话)",
"option_dev_reset_tip1": "确认要重置应用吗,重置应用将会失去所有设置内容(包括设置的置顶猫圈),但是可能可以解决一些因为浏览器缓存导致的奇怪问题。",
"btn_pass": "跳过",
"wel_home_tip": "下面是一点点简单的使用引导 …… 如果不想看可以直接戳跳过(小声),但是也没多长啦",
"wel_select_language": "选择语言",
"wel_finish": "该说的都说了 —— 那么就可以愉快的用啦(大声),如果遇到什么奇怪的问题,尽管来 CatHub 仓库问哦。",
"chat_msg_menu_at": "提及",
"option_view_view": "页面",
"option_view_initial_scale": "缩放比例",
"option_view_initial_scale_tip": "调整页面在移动端的缩放比例",
"chat_readed": "已标记为已读",
"chat_type_group": "喵圈",
"chat_type_user": "猫友",
"chat_chat_forward_success": "喵话已转发",
"chat_msg_forward_pan": "转发喵话",
"option_dev_chat_use_breakline": "使用 shift enter 换行",
"option_dev_chat_use_breakline_tip": "I have a shift, I have an enter ...",
"option_dev_chat_use_breakline_tip_1": "开启 shift enter 换行可能会在一些拥有特殊选词模式的输入法上出现问题,如 微软注音2003、新注音2003 和 绝大部分很早期的拼音输入法;如果在使用的时候遇到问题可以尝试关闭此功能。(或者换个更现代的输入法)",
"bulletin_show_tip": "点击展开",
"option_dev_msg_type": "喵话类型",
"option_dev_msg_type_tip": "[CQ:face,id=1]喵喵喵👋,这个选项将会强制覆盖自动检测",
"option_dev_msg_type_auto": "自动检测",
"chat_chat_info_group_card": "我的喵圈名字",
"chat_chat_info_group_card_tip": "宇宙无敌猫星书记官",
"chat_chat_info_group_name": "猫圈名称",
"chat_chat_info_group_name_tip": "= 猫圈客户端喵语化摸鱼小组 =",
"chat_chat_info_silence_all": "全猫禁言",
"chat_chat_info_silence_all_tip": "你们是不整点活不开心是吧",
"btn_accept": "同意",
"btn_reject": "拒绝",
"sys_notice_new_friend": "新猫友",
"sys_notice": "系统猫话",
"chat_msg_menu_remove": "移出猫圈",
"sys_notice_new_group_nmember": "入圈申请",
"sys_notice_new_group_nmember_add": "申请加入:",
"sys_notice_new_group_nmember_no_comment": "(没有猫猫介绍)",
"option_view_auto_gtk": "自动跟随 GTK 主题",
"option_view_auto_gtk_tip": "(实验性)自动从 GTK 配置获取主题配色",
"option_view_auto_win_color": "自动跟随 Windows 主题色",
"option_view_auto_win_color_tip": "自动获取 Windows 的主题色设置并应用",
"option_view_auto_win_color_tip_1": "获取 Windows 主题色失败:",
"option_view_background": "背景猫图",
"option_view_background_tip": "嘿嘿嘿(痴呆",
"option_view_background_blur": "猫图模糊",
"option_view_background_blur_tip": "什么都看不见了(恼",
"pop_chat_image_compression_fail": "压缩猫图失败",
"pop_chat_image_compression": "正在压缩猫图 ……",
"chat_msg_menu_remove_tip": "真的要将 {user} 赶出猫圈",
"option_view_no_window": "去除窗口框架",
"option_view_no_window_tip": "沉浸式没圆角体验(无端",
"option_dev_restart": "重启应用",
"option_dev_restart_tip": "99% 的特性都能通过重启解决!",
"btn_close": "关闭",
"btn_open": "打开",
"pop_send_file_fail": "发送文件失败",
"pop_send_file_err": "发送文件错误",
"pop_send_file": "正在发送文件 {percent}%",
"chat_fun_menu_file": "文件",
"chat_view_file_viewer": "文件预览",
"chat_temp": "临时会话",
"pop_friend_added": "添加猫友 {name} 成功!",
"option_view_no_window_mac_style": "MacOS 样式标题栏",
"option_view_no_window_mac_style_tip": "看Mac mini炫耀",
"chat_temp_from": "来自猫圈:{group}",
"list_menu_top": "置顶",
"list_menu_canceltop": "取消置顶",
"list_menu_remove": "删除",
"list_menu_readed": "标记已读",
"friend_group": "猫圈"
}

View File

@ -175,8 +175,6 @@
"pop_option_dev_debug_msg_tip_1": "你不是人(逃",
"pop_print_all_pop": "即将输出所有应用消息5s ……",
"log_cq_msg_parsed": "解析 CQ 消息结果",
"chat_chat_info_option_top": "置顶",
"chat_chat_info_option_top_tip": "再多看我一眼(无端",
"log_com_err": "创建连接失败",
"sw_ready": "应用已通过 service worker 服务从缓存中加载,更多信息请查看 https://goo.gl/AFskqB。",
"sw_registered": "Service worker 服务注册成功。",
@ -288,5 +286,10 @@
"pop_friend_added": "添加好友 {name} 成功!",
"option_view_no_window_mac_style": "MacOS 样式标题栏",
"option_view_no_window_mac_style_tip": "看Mac mini炫耀",
"chat_temp_from": "来自群聊:{group}"
"chat_temp_from": "来自群聊:{group}",
"list_menu_top": "置顶",
"list_menu_canceltop": "取消置顶",
"list_menu_remove": "删除",
"list_menu_readed": "标记已读",
"friend_group": "群组"
}

View File

@ -289,5 +289,10 @@
"pop_friend_added": "成功新增聯絡人 {name}",
"option_view_no_window_mac_style": "macOS 風格標題列",
"option_view_no_window_mac_style_tip": "聽說 SS 很喜歡 macOS 的標題列風格",
"chat_temp_from": "來自群組:{group}"
"chat_temp_from": "來自群組:{group}",
"list_menu_top": "釘選",
"list_menu_canceltop": "取消釘選",
"list_menu_remove": "删除",
"list_menu_readed": "標示為已讀",
"friend_group": "群組"
}

View File

@ -295,5 +295,10 @@
"pop_friend_added": "成功新增聯絡人 {name}",
"option_view_no_window_mac_style": "macOS 風格 title bar",
"option_view_no_window_mac_style_tip": "nosumi",
"chat_temp_from": "來自 group{group}"
"chat_temp_from": "來自 group{group}",
"list_menu_top": "置頂",
"list_menu_canceltop": "取消置頂",
"list_menu_remove": "删除",
"list_menu_readed": "標示為已讀",
"friend_group": "Group"
}

View File

@ -6,7 +6,7 @@
-->
<template>
<div :class="'friend-body' + (select ? ' active' : '')"
<div :class="'friend-body' + (select ? ' active' : (menu ? ' onmenu' : ''))"
:id="'user-' + (data.user_id ? data.user_id : data.group_id)"
:data-name="data.user_id ? data.nickname : data.group_name" :data-nickname="data.user_id ? data.nickname : ''"
:data-type="data.user_id ? 'friend' : 'group'">
@ -45,7 +45,7 @@ import { getTrueLang } from '@/function/util'
export default defineComponent({
name: 'FriendBody',
props: ['data', 'select'],
props: ['data', 'select', 'menu'],
data () {
return {
trueLang: getTrueLang()

View File

@ -7,7 +7,7 @@ export interface RunTimeDataElem {
botInfo: { [key: string]: any }
loginInfo: { [key: string]: any }
userList: (UserFriendElem & UserGroupElem)[]
showList?: (UserFriendElem & UserGroupElem)[]
showList: (UserFriendElem & UserGroupElem)[]
onMsgList: (UserFriendElem & UserGroupElem)[]
systemNoticesList?: { [key: string]: any }
chatInfo: ChatInfoElem
@ -26,7 +26,8 @@ export interface RunTimeDataElem {
},
loginWaveTimer?: any,
isElectron: boolean,
connectSsl: boolean
connectSsl: boolean,
classes: any[]
},
messageList: any[]
mergeMessageList?: [],
@ -81,6 +82,7 @@ export interface BaseChatInfoElem {
export interface UserFriendElem {
group_id: number,
group_name: string,
py_name?: string,
member_count?: number,
admin_flag?: boolean,
new_msg?: boolean,
@ -94,6 +96,7 @@ export interface UserGroupElem {
user_id: number,
nickname: string,
remark: string,
py_name?: string,
class_id?: number,
new_msg?: boolean,
raw_msg?: string,

View File

@ -15,6 +15,7 @@ import app from '@/main'
import Option from './option'
import Util from './util'
import xss from 'xss'
import pinyin from 'pinyin'
import { Md5 } from 'ts-md5'
import { reactive, nextTick, markRaw, defineAsyncComponent } from 'vue'
@ -22,6 +23,7 @@ import { PopInfo, PopType, Logger, LogType } from './base'
import { Connector, login } from './connect'
import { GroupMemberInfoElem, UserFriendElem, UserGroupElem, MsgItemElem, RunTimeDataElem, BotMsgType } from './elements/information'
import { NotificationElem } from './elements/system'
import { IPinyinOptions } from 'pinyin/lib/declare'
const popInfo = new PopInfo()
@ -65,6 +67,7 @@ export function parse(str: string) {
case 'setFriendAdd' :
case 'setGroupAdd' : updateSysInfo(head); break
case 'loadFileBase' : loadFileBase(echoList, msg); break
case 'getClassInfo' : saveClassInfo(msg); break
}
}
} else {
@ -163,7 +166,7 @@ function saveLoginInfo(data: { [key: string]: any }) {
'getMoreLoginInfo'
)
// GA将 QQ 号 MD5 编码后用于用户识别码
if (Option.get('open_ga_user') === true) {
if (Option.get('open_ga_user') == true && process.env.NODE_ENV == 'production') {
const userId = Md5.hashStr(data.uin)
app.config.globalProperties.$gtag.config({
user_id: userId
@ -174,6 +177,21 @@ function saveLoginInfo(data: { [key: string]: any }) {
}
function saveUser(list: (UserFriendElem & UserGroupElem)[]) {
// 拼音处理
// 为所有项目追加拼音名称
const pyConfig = {
style: 0
} as IPinyinOptions
list.forEach((item, index) => {
let py_name = ''
if(item.group_id) {
py_name = pinyin(item.group_name, pyConfig).join('')
} else {
py_name = pinyin(item.nickname, pyConfig).join('') + ',' +
pinyin(item.remark, pyConfig).join('')
}
list[index].py_name = py_name
})
runtimeData.userList = runtimeData.userList.concat(list)
// 刷新置顶列表
const info = runtimeData.sysConfig.top_info as { [key: string]: number[] } | null
@ -191,6 +209,25 @@ function saveUser(list: (UserFriendElem & UserGroupElem)[]) {
}
}
function saveClassInfo(list: any) {
// 对 classes 列表按拼音重新排序
const names = [] as string[]
list.data.forEach((item: any) => {
names.push(Object.values(item)[0] as string)
})
const sortedData = names.sort(pinyin.compare)
const back = [] as any[]
sortedData.forEach((name) => {
list.data.forEach((item: any) => {
if((Object.values(item)[0] as string) == name)
back.push(item)
})
})
runtimeData.tags.classes = back
}
function saveGroupMember(data: GroupMemberInfoElem[]) {
// 筛选列表
const adminList = data.filter((item: GroupMemberInfoElem) => {
@ -355,7 +392,7 @@ function saveSendedMsg(echoList: string[], msg: any) {
}
function loadFileBase(echoList: string[], msg: any) {
const url = msg.data.url
let url = msg.data.url
const msgId = echoList[1]
const ext = echoList[2]
if(url) {
@ -367,6 +404,13 @@ function loadFileBase(echoList: string[], msg: any) {
}
})
if(msgIndex !== -1) {
if(document.location.protocol == 'https:') {
// 判断文件 URL 的协议
// PSChrome 不会对 http 文件进行协议升级
if(url.toLowerCase().startsWith('http:')) {
url = 'https' + url.substring(url.indexOf('://'))
}
}
runtimeData.messageList[msgIndex].fileView.url = url
runtimeData.messageList[msgIndex].fileView.ext = ext
}
@ -901,7 +945,8 @@ const baseRuntime = {
viewer: { index: 0 },
msgType: BotMsgType.JSON,
isElectron: false,
connectSsl: false
connectSsl: false,
classes: []
},
chatInfo: {
show: { type: '', id: 0, name: '', avatar: '' },
@ -917,9 +962,10 @@ const baseRuntime = {
},
pageView: {
chatView: markRaw(defineAsyncComponent(() => import('@/pages/Chat.vue'))),
msgView: markRaw(defineAsyncComponent(() => import('@/pages/Chat.vue')))
msgView: markRaw(defineAsyncComponent(() => import('@/components/MsgBody.vue')))
},
userList: [],
showList: [],
systemNoticesList: [],
onMsgList: [],
loginInfo: {},

View File

@ -733,6 +733,7 @@ export function reloadUsers() {
Connector.send('get_friend_list', {}, 'getFriendList')
Connector.send('get_group_list', {}, 'getGroupList')
Connector.send('get_system_msg', {}, 'getSystemMsg')
Connector.send('get_class_info', {}, "getClassInfo")
}
export default {

View File

@ -8,6 +8,7 @@ import App from './App.vue'
import { createApp } from 'vue'
import { createI18n } from 'vue-i18n'
import { FontAwesomeIcon } from '@fortawesome/vue-fontawesome'
import './registerServiceWorker'
@ -42,6 +43,8 @@ app.use(VueClipboard)
app.use(InfiniteScroll)
app.use(VueGtag)
app.component('font-awesome-icon', FontAwesomeIcon)
app.mount('#app')
export default app

View File

@ -282,7 +282,7 @@
<!-- 消息右击菜单 -->
<div :class="'msg-menu' + (runtimeData.sysConfig.opt_no_window ? ' withBar': '')">
<div v-show="tags.showMsgMenu" class="msg-menu-bg" @click="closeMsgMenu"></div>
<div :class="tags.showMsgMenu ? 'ss-card menu show' : 'ss-card menu'" id="msgMenu">
<div :class="tags.showMsgMenu ? 'ss-card msg-menu-body show' : 'ss-card msg-menu-body'" id="msgMenu">
<div @click="replyMsg(true)" v-show="tags.menuDisplay.relpy">
<div><svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 512 512"><path d="M511.1 63.1v287.1c0 35.25-28.75 63.1-64 63.1h-144l-124.9 93.68c-7.875 5.75-19.12 .0497-19.12-9.7v-83.98h-96c-35.25 0-64-28.75-64-63.1V63.1c0-35.25 28.75-63.1 64-63.1h384C483.2 0 511.1 28.75 511.1 63.1z"/></svg></div>
<a>{{ $t('chat_msg_menu_reply') }}</a>

View File

@ -47,12 +47,45 @@
</svg>
</label>
</div>
<div id="friend-list-body" v-infinite-scroll="addLoad" infinite-scroll-watch-disabled="loading"
:class="(runtimeData.tags.openSideBar ? 'open' : '')"
infinite-scroll-distance="10" infinite-scroll-immediate-check="false">
<FriendBody v-for="item in runtimeData.showList"
<div :class="(runtimeData.tags.openSideBar ? 'open' : '')">
<template v-if="runtimeData.showList.length <= 0">
<template v-for="name in runtimeData.tags.classes"
:key="'class-' + Object.keys(name)[0]">
<div :class="'exp-body' + (classStatus[Object.keys(name)[0]] == true ? ' open' : '')">
<header class="exp-header" @click="classClick(Object.keys(name)[0])">
<div></div>
<span>{{ Object.values(name)[0] }}</span>
<a>{{ runtimeData.userList.filter((get) => { return get.class_id == Number(Object.keys(name)[0]) }).length }}</a>
</header>
<div :id="'class-' + Object.keys(name)[0]">
<FriendBody
v-for="item in runtimeData.userList.filter((get) => { return get.class_id == Number(Object.keys(name)[0]) })"
:key="'fb-' + (item.user_id ? item.user_id : item.group_id)" :data="item"
@click="userClick(item, $event)">
</FriendBody>
</div>
</div>
</template>
<div :class="'exp-body' + (classStatus['-1'] == true ? ' open' : '')">
<header class="exp-header" @click="classClick('-1')">
<div></div>
<span>{{ $t('friend_group') }}</span>
<a>{{ runtimeData.userList.filter((get) => { return get.class_id == undefined }).length }}</a>
</header>
<div>
<FriendBody
v-for="item in runtimeData.userList.filter((get) => { return get.class_id == undefined })"
:key="'fb-' + (item.user_id ? item.user_id : item.group_id)" :data="item"
@click="userClick(item, $event)">
</FriendBody>
</div>
</div>
</template>
<!-- 搜索用的 -->
<FriendBody v-for="item in runtimeData.showList.length > 0 ? runtimeData.showList : []"
:key="'fb-' + (item.user_id ? item.user_id : item.group_id)" :data="item"
@click="userClick(item, $event)"></FriendBody>
@click="userClick(item, $event)">
</FriendBody>
</div>
</div>
<div>
@ -68,13 +101,12 @@
</template>
<script lang="ts">
import { defineComponent } from 'vue'
import FriendBody from '@/components/FriendBody.vue'
import { defineComponent } from 'vue'
import { BaseChatInfoElem, UserFriendElem } from '@/function/elements/information'
import { UserGroupElem } from '@/function/elements/information'
import { Connector } from '@/function/connect'
import { runtimeData } from '@/function/msg'
import { reloadUsers } from '@/function/util'
@ -85,10 +117,10 @@ export default defineComponent({
data () {
return {
runtimeData: runtimeData,
listPage: 1,
loading: false,
isSearch: false,
searchInfo: ''
searchInfo: '',
classStatus: {} as {[key: string]: boolean}
}
},
methods: {
@ -104,8 +136,6 @@ export default defineComponent({
}
this.isSearch = false
this.searchInfo = ''
runtimeData.showList = this.list.slice(0, 15)
this.listPage = 1
const back = {
type: data.user_id ? 'user' : 'group',
id: data.user_id ? data.user_id : data.group_id,
@ -131,18 +161,6 @@ export default defineComponent({
barMsg.click()
}
},
/**
* 分段加载回调
*/
addLoad () {
if (!this.isSearch) {
this.loading = true
runtimeData.showList = runtimeData.showList?.concat(this.list.slice(this.listPage * 10, (this.listPage + 1) * 10))
this.listPage++
this.loading = false
}
},
/**
* 列表搜索
@ -152,15 +170,15 @@ export default defineComponent({
const value = (event.target as HTMLInputElement).value
if (value !== '') {
this.isSearch = true
runtimeData.showList = this.list.filter((item: UserFriendElem & UserGroupElem) => {
this.runtimeData.showList = this.list.filter((item: UserFriendElem & UserGroupElem) => {
const name = (item.user_id ? (item.nickname + item.remark) : item.group_name).toLowerCase()
const py = item.py_name ? item.py_name : ''
const id = item.user_id ? item.user_id : item.group_id
return name.indexOf(value.toLowerCase()) !== -1 || id.toString() === value
return (value.length > 4 && py.indexOf(value.toLowerCase()) != -1) || name.indexOf(value.toLowerCase()) != -1 || id.toString() === value
})
} else {
this.isSearch = false
runtimeData.showList = this.list.slice(0, 15)
this.listPage = 1
this.runtimeData.showList = [] as any[]
}
},
@ -176,24 +194,55 @@ export default defineComponent({
*/
openLeftBar () {
runtimeData.tags.openSideBar = !runtimeData.tags.openSideBar
}
},
watch: {
list: {
deep: true,
/**
* 初始无限列表
* @param val 完整列表数据
*/
handler (val) {
if(!this.isSearch) {
//
runtimeData.showList = val.slice(0, 15)
this.listPage = 1
}
},
classClick(id: string) {
if(this.classStatus[id]) {
this.classStatus[id] = !this.classStatus[id]
} else {
this.classStatus[id] = true
}
}
}
})
</script>
<style scoped>
.exp-header {
color: var(--color-font);
align-items: center;
border-radius: 7px;
cursor: pointer;
margin: 0 10px;
padding: 10px;
display: flex;
}
.exp-header:hover {
background: var(--color-card-2);
}
.exp-header > div {
background: var(--color-main);
margin-right: 10px;
border-radius: 7px;
height: 1rem;
width: 5px;
}
.exp-header > span {
flex: 1;
}
.exp-header > a {
color: var(--color-font-2);
font-size: 0.9rem;
}
.exp-body > div {
/* transition: transform .3s;
transform-origin: top; */
transform: scaleY(0);
height: 0;
}
.exp-body.open > div {
transform: scaleY(1);
height: unset;
}
</style>

View File

@ -105,10 +105,13 @@
</ul>
<div class="chat-info-tab-body layui-tab-content">
<div class="layui-tab-item layui-show chat-info-tab-member">
<div @click="startChat(item)" v-for="item in chat.info.group_members" :key="'chatinfomlist-' + item.user_id">
<div class="search-view">
<input :placeholder="$t('base_search')" @input="searchList">
</div>
<div @click="startChat(item)" v-for="item in number_cache.length > 0 ? number_cache : chat.info.group_members" :key="'chatinfomlist-' + item.user_id">
<img loading="lazy" :src="`https://q1.qlogo.cn/g?b=qq&s=0&nk=${item.user_id}`">
<div>
<a>{{ item.nickname }}</a>
<a>{{ item.card ? item.card : item.nickname }}</a>
<svg v-if="item.role === 'owner'" xmlns="http://www.w3.org/2000/svg"
viewBox="0 0 576 512">
<path
@ -160,7 +163,7 @@ import BulletinBody from '@/components/BulletinBody.vue'
import FileBody from '@/components/FileBody.vue'
import OptInfo from './options/OptInfo.vue'
import { defineComponent } from 'vue'
import { defineComponent, toRaw } from 'vue'
import { getTrueLang } from '@/function/util'
import { runtimeData } from '@/function/msg'
import { UserFriendElem, UserGroupElem } from '@/function/elements/information'
@ -173,7 +176,8 @@ export default defineComponent({
return {
runtimeData: runtimeData,
trueLang: getTrueLang(),
isTop: false
isTop: false,
number_cache: [] as any[]
}
},
methods: {
@ -235,7 +239,36 @@ export default defineComponent({
})
}
},
searchList(event: Event) {
const value = (event.target as HTMLInputElement).value
if (value !== '') {
this.number_cache = toRaw(this.chat.info.group_members)
this.number_cache = this.number_cache.filter((item) => {
const name = item.card.toLowerCase() + '('+ item.nickname.toLowerCase() + ')'
const id = item.user_id
return name.indexOf(value.toLowerCase()) != -1 || id.toString() === value
})
} else {
this.number_cache = [] as any[]
}
}
}
})
</script>
<style scoped>
.search-view {
background: transparent !important;
margin-top: -10px;
}
.search-view > input {
background: var(--color-card-1);
border-radius: 7px;
margin: 0 -10px;
padding: 0 10px;
height: 35px;
width: 100%;
border: 0;
}
</style>

View File

@ -28,7 +28,15 @@
</div>
</div>
</div>
<div id="message-list-body" :class="(runtimeData.tags.openSideBar ? 'open' : '')">
<BcMenu :data="listMenu" @close="listMenuClose" name="messages-menu">
<ul>
<li icon="fa-solid fa-thumbtack" id="top">{{ $t('list_menu_top') }}</li>
<li icon="fa-solid fa-grip-lines" id="canceltop">{{ $t('list_menu_canceltop') }}</li>
<li icon="fa-solid fa-trash-can" id="remove">{{ $t('list_menu_remove') }}</li>
<li icon="fa-solid fa-check-to-slot" id="readed">{{ $t('list_menu_readed') }}</li>
</ul>
</BcMenu>
<div id="message-list-body" :class="(runtimeData.tags.openSideBar ? 'open' : '')" style="overflow: scroll;">
<!-- 系统信息 -->
<FriendBody key="inMessage--10000"
v-if="runtimeData.systemNoticesList && Object.keys(runtimeData.systemNoticesList).length > 0"
@ -38,9 +46,11 @@
<!-- 其他消息 -->
<FriendBody v-for="item in runtimeData.onMsgList"
:key="'inMessage-' + item.user_id ? item.user_id : item.group_id"
:select="chat.show.id === item.user_id || (chat.show.id === item.group_id && chat.group_name != '')" :data="item"
@click="userClick(item)" @contextmenu.prevent="readMsg(item)" @touchstart="readStart"
@touchend="readEnd(item)">
:select="chat.show.id === item.user_id || (chat.show.id === item.group_id && chat.group_name != '')"
:menu="menu.select && menu.select == item"
:data="item"
@click="userClick(item)"
@contextmenu.prevent="listMenuShow($event, item)">
</FriendBody>
</div>
</div>
@ -59,22 +69,34 @@
<script lang="ts">
import app from '@/main'
import FriendBody from '@/components/FriendBody.vue'
import BcMenu from 'vue3-bcui/packages/bc-menu'
import Menu from 'vue3-bcui/packages/bc-menu/index'
import Option from '@/function/option'
import { defineComponent } from 'vue'
import { runtimeData, notificationList } from '@/function/msg'
import { UserFriendElem, UserGroupElem } from '@/function/elements/information'
import { getRaw as getOpt, run as runOpt } from '@/function/option'
import { loadHistoryMessage } from '@/function/util'
import { Logger, LogType, PopInfo, PopType } from '@/function/base'
import { PopInfo, PopType } from '@/function/base'
import { MenuStatue } from 'vue3-bcui/packages/dist/types'
import { library } from '@fortawesome/fontawesome-svg-core'
import { faThumbTack, faTrashCan, faCheckToSlot, faGripLines } from '@fortawesome/free-solid-svg-icons'
export default defineComponent({
name: 'VueMessages',
props: ['chat'],
components: { FriendBody },
components: { FriendBody, BcMenu },
data() {
return {
runtimeData: runtimeData,
trRead: false
trRead: false,
listMenu: {
show: false,
point: { x: 0, y: 0 }
} as MenuStatue,
menu: Menu.append
}
},
methods: {
@ -164,19 +186,6 @@ export default defineComponent({
new PopInfo().add(
PopType.INFO, app.config.globalProperties.$t('chat_readed'))
},
readStart() {
const logger = new Logger()
this.trRead = false
setTimeout(() => {
logger.add(LogType.UI, "列表触屏长按触发。")
this.trRead = true
}, 800)
},
readEnd(data: (UserFriendElem & UserGroupElem)) {
if (this.trRead) {
this.readMsg(data)
}
},
/**
* 清空消息列表
@ -197,7 +206,122 @@ export default defineComponent({
})
}
}
},
/**
* 列表菜单关闭事件
* @param id 选择的菜单 ID
*/
listMenuClose(id: string) {
this.listMenu.show = false
const item = this.menu.select
if(id) {
switch(id) {
case 'readed': this.readMsg(item); break
case 'remove': {
const index = runtimeData.onMsgList.findIndex((get) => {
return item == get
})
runtimeData.onMsgList.splice(index, 1)
break
}
case 'top': this.saveTop(true); break
case 'canceltop': this.saveTop(false); break
}
}
this.menu.select = undefined
},
/**
* 保存置顶信息
* @param event 点击事件
*/
saveTop(value: boolean) {
const id = runtimeData.loginInfo.uin
// cookie JSON
let topInfo = runtimeData.sysConfig.top_info as { [key: string]: number[] }
if (topInfo == null) {
topInfo = {}
}
//
let topList = topInfo[id]
//
if (value) {
if (topList) {
if (topList.indexOf(this.chat.show.id) < 0) {
topList.push(this.chat.show.id)
}
} else {
topList = [this.chat.show.id]
}
} else {
if (topList) {
topList.splice(topList.indexOf(this.chat.show.id), 1)
}
}
// cookie
if (topList) {
topInfo[id] = topList
Option.save('top_info', topInfo)
}
//
for (let i = 0; i < runtimeData.onMsgList.length; i++) {
const item = runtimeData.onMsgList[i]
if (item.user_id == this.chat.show.id || item.group_id == this.chat.show.id) {
runtimeData.onMsgList[i].always_top = value
break
}
}
//
const newList = [] as (UserFriendElem & UserGroupElem)[]
let topNum = 1
runtimeData.onMsgList.forEach((item) => {
//
if (item.always_top === true) {
newList.unshift(item)
topNum++
} else if (item.new_msg === true) {
newList.splice(topNum - 1, 0, item)
} else {
newList.push(item)
}
})
runtimeData.onMsgList = newList
},
/**
* 显示列表菜单
* @param item 菜单内容
*/
listMenuShow(event: Event, item: (UserFriendElem & UserGroupElem)) {
const info = this.menu.set('messages-menu', event as MouseEvent)
info.list = ['top', 'remove', 'readed']
//
if(item.always_top) {
info.list = ['canceltop', 'readed']
}
this.listMenu = info
this.menu.select = item
}
},
mounted() {
library.add(faCheckToSlot, faThumbTack, faTrashCan, faGripLines)
}
})
</script>
<style>
.menu div.item > a {
font-size: 0.9rem !important;
}
.menu div.item > svg {
margin: 3px 10px 3px 0 !important;
font-size: 1rem !important;
}
@media (max-width: 700px) {
.menu {
width: 140px !important;
}
}
</style>

View File

@ -8,22 +8,6 @@
<template>
<div class="info-pan-set" style="padding:0">
<!-- 公用设置 -->
<div class="opt-item">
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 384 512">
<path
d="M32 32C32 14.3 46.3 0 64 0H320c17.7 0 32 14.3 32 32s-14.3 32-32 32H290.5l11.4 148.2c36.7 19.9 65.7 53.2 79.5 94.7l1 3c3.3 9.8 1.6 20.5-4.4 28.8s-15.7 13.3-26 13.3H32c-10.3 0-19.9-4.9-26-13.3s-7.7-19.1-4.4-28.8l1-3c13.8-41.5 42.8-74.8 79.5-94.7L93.5 64H64C46.3 64 32 49.7 32 32zM160 384h64v96c0 17.7-14.3 32-32 32s-32-14.3-32-32V384z" />
</svg>
<div>
<span>{{ $t('chat_chat_info_option_top') }}</span>
<span>{{ $t('chat_chat_info_option_top_tip') }}</span>
</div>
<label class="ss-switch">
<input type="checkbox" @change="saveTop" v-model="isTop">
<div>
<div></div>
</div>
</label>
</div>
<!-- 群设置 -->
<template v-if="type == 'group'">
<div class="opt-item"
@ -56,12 +40,8 @@
</template>
<script lang="ts">
import app from '@/main'
import Option from '@/function/option'
import { defineComponent } from 'vue'
import { runtimeData } from '@/function/msg'
import { UserGroupElem, UserFriendElem } from '@/function/elements/information'
import { Connector } from '@/function/connect'
export default defineComponent({
@ -69,8 +49,7 @@ export default defineComponent({
props: ['type', 'chat'],
data() {
return {
runtimeData: runtimeData,
isTop: false
runtimeData: runtimeData
}
},
methods: {
@ -107,83 +86,7 @@ export default defineComponent({
'setGroupName'
)
}
},
/**
* 保存置顶信息
* @param event 点击事件
*/
saveTop(event: Event) {
const id = runtimeData.loginInfo.uin
// cookie JSON
let topInfo = runtimeData.sysConfig.top_info as { [key: string]: number[] }
if (topInfo == null) {
topInfo = {}
}
//
let topList = topInfo[id]
//
const sender = event.currentTarget as HTMLInputElement
const value = sender.checked
//
if (value) {
if (topList) {
if (topList.indexOf(this.chat.show.id) < 0) {
topList.push(this.chat.show.id)
}
} else {
topList = [this.chat.show.id]
}
} else {
if (topList) {
topList.splice(topList.indexOf(this.chat.show.id), 1)
}
}
// cookie
if (topList) {
topInfo[id] = topList
Option.save('top_info', topInfo)
}
//
for (let i = 0; i < runtimeData.onMsgList.length; i++) {
const item = runtimeData.onMsgList[i]
if (item.user_id == this.chat.show.id || item.group_id == this.chat.show.id) {
runtimeData.onMsgList[i].always_top = value
break
}
}
//
const newList = [] as (UserFriendElem & UserGroupElem)[]
let topNum = 1
runtimeData.onMsgList.forEach((item) => {
//
if (item.always_top === true) {
newList.unshift(item)
topNum++
} else if (item.new_msg === true) {
newList.splice(topNum - 1, 0, item)
} else {
newList.push(item)
}
})
runtimeData.onMsgList = newList
},
/**
* 检查并修改 isTop
*/
updateIsTop() {
if (runtimeData.sysConfig.top_info != undefined) {
let topList = runtimeData.sysConfig.top_info[runtimeData.loginInfo.uin]
if (topList != undefined) {
this.isTop = topList.indexOf(this.chat.show.id) >= 0
}
}
}
},
mounted() {
this.updateIsTop()
this.$watch(() => runtimeData.chatInfo.show.id, () => { this.$nextTick(this.updateIsTop) })
}
})
</script>

335
yarn.lock
View File

@ -942,6 +942,13 @@
dependencies:
regenerator-runtime "^0.13.11"
"@babel/runtime@^7.7.2":
version "7.21.0"
resolved "https://registry.npmmirror.com/@babel/runtime/-/runtime-7.21.0.tgz#5b55c9d394e5fcf304909a8b00c07dc217b56673"
integrity sha512-xwII0//EObnq89Ji5AKYQaRYiW/nZ3llSv29d49IuxPhKbtJoLP+9QUUZ4nVragQVtaVGeZrpB+ZtG/Pdy/POw==
dependencies:
regenerator-runtime "^0.13.11"
"@babel/template@^7.0.0", "@babel/template@^7.18.10":
version "7.18.10"
resolved "https://registry.npmmirror.com/@babel/template/-/template-7.18.10.tgz#6f9134835970d1dbf0835c0d100c9f38de0c5e71"
@ -1031,6 +1038,37 @@
minimatch "^3.0.4"
strip-json-comments "^3.1.1"
"@fortawesome/fontawesome-common-types@6.4.0":
version "6.4.0"
resolved "https://registry.npmmirror.com/@fortawesome/fontawesome-common-types/-/fontawesome-common-types-6.4.0.tgz#88da2b70d6ca18aaa6ed3687832e11f39e80624b"
integrity sha512-HNii132xfomg5QVZw0HwXXpN22s7VBHQBv9CeOu9tfJnhsWQNd2lmTNi8CSrnw5B+5YOmzu1UoPAyxaXsJ6RgQ==
"@fortawesome/fontawesome-svg-core@^6.3.0":
version "6.4.0"
resolved "https://registry.npmmirror.com/@fortawesome/fontawesome-svg-core/-/fontawesome-svg-core-6.4.0.tgz#3727552eff9179506e9203d72feb5b1063c11a21"
integrity sha512-Bertv8xOiVELz5raB2FlXDPKt+m94MQ3JgDfsVbrqNpLU9+UE2E18GKjLKw+d3XbeYPqg1pzyQKGsrzbw+pPaw==
dependencies:
"@fortawesome/fontawesome-common-types" "6.4.0"
"@fortawesome/free-regular-svg-icons@^6.3.0":
version "6.4.0"
resolved "https://registry.npmmirror.com/@fortawesome/free-regular-svg-icons/-/free-regular-svg-icons-6.4.0.tgz#cacc53bd8d832d46feead412d9ea9ce80a55e13a"
integrity sha512-ZfycI7D0KWPZtf7wtMFnQxs8qjBXArRzczABuMQqecA/nXohquJ5J/RCR77PmY5qGWkxAZDxpnUFVXKwtY/jPw==
dependencies:
"@fortawesome/fontawesome-common-types" "6.4.0"
"@fortawesome/free-solid-svg-icons@^6.3.0":
version "6.4.0"
resolved "https://registry.npmmirror.com/@fortawesome/free-solid-svg-icons/-/free-solid-svg-icons-6.4.0.tgz#48c0e790847fa56299e2f26b82b39663b8ad7119"
integrity sha512-kutPeRGWm8V5dltFP1zGjQOEAzaLZj4StdQhWVZnfGFCvAPVvHh8qk5bRrU4KXnRRRNni5tKQI9PBAdI6MP8nQ==
dependencies:
"@fortawesome/fontawesome-common-types" "6.4.0"
"@fortawesome/vue-fontawesome@^3.0.3":
version "3.0.3"
resolved "https://registry.npmmirror.com/@fortawesome/vue-fontawesome/-/vue-fontawesome-3.0.3.tgz#633e2998d11f7d4ed41f0d5ea461a22ec9b9d034"
integrity sha512-KCPHi9QemVXGMrfuwf3nNnNo129resAIQWut9QTAMXmXqL2ErABC6ohd2yY5Ipq0CLWNbKHk8TMdTXL/Zf3ZhA==
"@gar/promisify@^1.0.1":
version "1.1.3"
resolved "https://registry.npmmirror.com/@gar/promisify/-/promisify-1.1.3.tgz#555193ab2e3bb3b6adc3d551c9c030d9e860daf6"
@ -1207,6 +1245,21 @@
lodash "^4.17.15"
tmp-promise "^3.0.2"
"@mapbox/node-pre-gyp@^1.0.4":
version "1.0.10"
resolved "https://registry.npmmirror.com/@mapbox/node-pre-gyp/-/node-pre-gyp-1.0.10.tgz#8e6735ccebbb1581e5a7e652244cadc8a844d03c"
integrity sha512-4ySo4CjzStuprMwk35H5pPbkymjv1SF3jGLj6rAHp/xT/RF7TL7bd9CTm1xDY49K2qF7jmR/g7k+SkLETP6opA==
dependencies:
detect-libc "^2.0.0"
https-proxy-agent "^5.0.0"
make-dir "^3.1.0"
node-fetch "^2.6.7"
nopt "^5.0.0"
npmlog "^5.0.1"
rimraf "^3.0.2"
semver "^7.3.5"
tar "^6.1.11"
"@node-ipc/js-queue@2.0.3":
version "2.0.3"
resolved "https://registry.npmmirror.com/@node-ipc/js-queue/-/js-queue-2.0.3.tgz#ac7fe33d766fa53e233ef8fedaf3443a01c5a4cd"
@ -1214,6 +1267,90 @@
dependencies:
easy-stack "1.0.1"
"@node-rs/jieba-android-arm-eabi@1.6.2":
version "1.6.2"
resolved "https://registry.npmmirror.com/@node-rs/jieba-android-arm-eabi/-/jieba-android-arm-eabi-1.6.2.tgz#e34836593a7d5144fc625c924d6957d888ac298e"
integrity sha512-DWRjc+RmSsiALdS7Ay1dI/Qh86M9tP20UKNeKKHKQLeVCl8isupUVLFxBdSLqmarPBJImh6nI67TTRpPfcOYMg==
"@node-rs/jieba-android-arm64@1.6.2":
version "1.6.2"
resolved "https://registry.npmmirror.com/@node-rs/jieba-android-arm64/-/jieba-android-arm64-1.6.2.tgz#727935efd7bbaccdc9d9454e61cb693fcd0b1c00"
integrity sha512-3T6+mG9ZR28eu1qe3Sh2DTR/eZVIaAQaaR5C2UHTsJfxVZSeGcd1ogoLgBom9iU3QDIa0kJCliH+GHiOmqr1xw==
"@node-rs/jieba-darwin-arm64@1.6.2":
version "1.6.2"
resolved "https://registry.npmmirror.com/@node-rs/jieba-darwin-arm64/-/jieba-darwin-arm64-1.6.2.tgz#184cb496d407c7cac45659c5b7c1494698c6abdc"
integrity sha512-CvYmRSYebd4gpBYzmLivB17M4faNAe3o3BQ1E3MvjmlEu/J43XD59rOTdSkbe5ZykstC4i/xhaXKWRG2gcaOig==
"@node-rs/jieba-darwin-x64@1.6.2":
version "1.6.2"
resolved "https://registry.npmmirror.com/@node-rs/jieba-darwin-x64/-/jieba-darwin-x64-1.6.2.tgz#1aa3ef1b290d5ebf63dd7cd5401ed55134356132"
integrity sha512-YcI9nNnYrNMhh2onnWnEkNdByYj0JbqPD4yF4GCmF4SsFRcEUEEnJrFE42FZoWzhDhUrE3hSU0uBjL+8iggr9w==
"@node-rs/jieba-freebsd-x64@1.6.2":
version "1.6.2"
resolved "https://registry.npmmirror.com/@node-rs/jieba-freebsd-x64/-/jieba-freebsd-x64-1.6.2.tgz#12ba9046f913d6b839e90e5c5d7ac209e330f46d"
integrity sha512-iaH/F6JWEkE1DCeC0MEsglBuHbRj03Rj/PMAMhLZBruQyVJaQU7WHVFEt+eN+FbR0cPLUhvj4oltPF2nGlVYFQ==
"@node-rs/jieba-linux-arm-gnueabihf@1.6.2":
version "1.6.2"
resolved "https://registry.npmmirror.com/@node-rs/jieba-linux-arm-gnueabihf/-/jieba-linux-arm-gnueabihf-1.6.2.tgz#0d6f1882798ff99e3b196f1f92676a47074bedc6"
integrity sha512-T2V1KZ7Xhorm3xVG4k52xw0pH8Q4UevAey4mEdA6NDwlCnScqqENfzgMpt8Egv5xpBExte8tebB1+LLACD6Khg==
"@node-rs/jieba-linux-arm64-gnu@1.6.2":
version "1.6.2"
resolved "https://registry.npmmirror.com/@node-rs/jieba-linux-arm64-gnu/-/jieba-linux-arm64-gnu-1.6.2.tgz#ebe31ad3b5cbc3d0800ac40a589798ce0d1f554f"
integrity sha512-sZcAa/MGy6LTlEIU6uON9uY/AorQLbWVEEZ3g4W8FHAyqtdEeOByNNZG84qZzjXlWZbsjKRETArpGH2QBaXeWQ==
"@node-rs/jieba-linux-arm64-musl@1.6.2":
version "1.6.2"
resolved "https://registry.npmmirror.com/@node-rs/jieba-linux-arm64-musl/-/jieba-linux-arm64-musl-1.6.2.tgz#8a7b613c6c8f673f5258c1e9a710a808942689d3"
integrity sha512-k+T34g1Pwr5sfpOSyjaCa9Mp4JCZ2XbP4pzrRsbc6ri7Y1tf9QzFR/fXgG5H24qRdLhzuXOJqdnJ6xVHTVUU9Q==
"@node-rs/jieba-linux-x64-gnu@1.6.2":
version "1.6.2"
resolved "https://registry.npmmirror.com/@node-rs/jieba-linux-x64-gnu/-/jieba-linux-x64-gnu-1.6.2.tgz#d12c7ef648f21357642f7c517e2859e669feaf3f"
integrity sha512-jcbrneEACIhZkVs3VOwhDWn7X8q18kfUugF3hhxW9ZzymuEMTUvcBFRWR18hk/WoHA5/MbcStr3ufteI+Wy5aw==
"@node-rs/jieba-linux-x64-musl@1.6.2":
version "1.6.2"
resolved "https://registry.npmmirror.com/@node-rs/jieba-linux-x64-musl/-/jieba-linux-x64-musl-1.6.2.tgz#a8a0106977785be1eb7b6afc5246024df5cffcf1"
integrity sha512-DbvAGsU+LNIiC7cK7uHsbM6ptwb0MMe4DSfYYhxJgt7GqDeWoDEd/fIGFO6GAgBLzFUpjAQgP6PBhCl55X2Avg==
"@node-rs/jieba-win32-arm64-msvc@1.6.2":
version "1.6.2"
resolved "https://registry.npmmirror.com/@node-rs/jieba-win32-arm64-msvc/-/jieba-win32-arm64-msvc-1.6.2.tgz#2997afa0e340ee2ffabf4c47d3a878d073e62ce6"
integrity sha512-I62/aVCCKxuTmCagvjyfj4rCbUaJTEjVModv2iWDw9lzt8UJtPd8C4XDe112r5I5AfkTfAHNZBe4k0zcE2NeuQ==
"@node-rs/jieba-win32-ia32-msvc@1.6.2":
version "1.6.2"
resolved "https://registry.npmmirror.com/@node-rs/jieba-win32-ia32-msvc/-/jieba-win32-ia32-msvc-1.6.2.tgz#a0c3a31f310ecc410dc94b8dd5c2f7cc6825e544"
integrity sha512-MizaOJGcYxHgeiGj/dEap+E0LZNuCxejh2NSjY5QMDMPOv8O7I0PdXSgdnOPypDTQE0dnO99r+TI2EUB0TDHxw==
"@node-rs/jieba-win32-x64-msvc@1.6.2":
version "1.6.2"
resolved "https://registry.npmmirror.com/@node-rs/jieba-win32-x64-msvc/-/jieba-win32-x64-msvc-1.6.2.tgz#3ee5d52014821c6dc41da8e4d9dc00a9e08dd070"
integrity sha512-d2W0IoxJ176jODE8wF6nNxfddYEaCtQ1xckJjIve/xHwUiBElnt81A41wZnfeyGx3pUaWMo4132s9EYJlN0Umg==
"@node-rs/jieba@^1.6.0":
version "1.6.2"
resolved "https://registry.npmmirror.com/@node-rs/jieba/-/jieba-1.6.2.tgz#64e1a5482b01e72a03ee4a395c71de0702133c70"
integrity sha512-1GA3RqfGgjemgMoh2wajdiApYEGZ7mjzsqIqEjHv7rHuIpSJSEgV+Jt81popd0DK0HLPNShVV3T3fSmTgv20Zw==
optionalDependencies:
"@node-rs/jieba-android-arm-eabi" "1.6.2"
"@node-rs/jieba-android-arm64" "1.6.2"
"@node-rs/jieba-darwin-arm64" "1.6.2"
"@node-rs/jieba-darwin-x64" "1.6.2"
"@node-rs/jieba-freebsd-x64" "1.6.2"
"@node-rs/jieba-linux-arm-gnueabihf" "1.6.2"
"@node-rs/jieba-linux-arm64-gnu" "1.6.2"
"@node-rs/jieba-linux-arm64-musl" "1.6.2"
"@node-rs/jieba-linux-x64-gnu" "1.6.2"
"@node-rs/jieba-linux-x64-musl" "1.6.2"
"@node-rs/jieba-win32-arm64-msvc" "1.6.2"
"@node-rs/jieba-win32-ia32-msvc" "1.6.2"
"@node-rs/jieba-win32-x64-msvc" "1.6.2"
"@nodelib/fs.scandir@2.1.5":
version "2.1.5"
resolved "https://registry.npmmirror.com/@nodelib/fs.scandir/-/fs.scandir-2.1.5.tgz#7619c2eb21b25483f6d167548b4cfd5a7488c3d5"
@ -2411,6 +2548,11 @@
resolved "https://registry.npmmirror.com/@xtuc/long/-/long-4.2.2.tgz#d291c6a4e97989b5c61d9acf396ae4fe133a718d"
integrity sha512-NuHqBY1PB/D8xU6s/thBgOAiAP7HOYDQ32+BFZILJ8ivkUkAHQnWfn6WhL79Owj1qmUnoN/YPhktdIoucipkAQ==
abbrev@1:
version "1.1.1"
resolved "https://registry.npmmirror.com/abbrev/-/abbrev-1.1.1.tgz#f8f2c887ad10bf67f634f005b6987fed3179aac8"
integrity sha512-nne9/IiQ/hzIhY6pdDnbBtz7DjPTKrY00P/zvPSm5pOFkl6xuGrGnXn/VtTNNfNtAfZ9/1RtehkszU9qcTii0Q==
accepts@~1.3.4, accepts@~1.3.5, accepts@~1.3.8:
version "1.3.8"
resolved "https://registry.npmmirror.com/accepts/-/accepts-1.3.8.tgz#0bf0be125b67014adcb0b0921e62db7bffe16b2e"
@ -2641,6 +2783,11 @@ app-builder-lib@22.14.13:
semver "^7.3.5"
temp-file "^3.4.0"
"aproba@^1.0.3 || ^2.0.0":
version "2.0.0"
resolved "https://registry.npmmirror.com/aproba/-/aproba-2.0.0.tgz#52520b8ae5b569215b354efc0caa3fe1e45a8adc"
integrity sha512-lYe4Gx7QT+MKGbDsA+Z+he/Wtef0BiwDOlK/XkBrdfsh9J/jPPXbX0tE9x9cl27Tmu5gg3QUbUrQYa/y+KOHPQ==
aproba@^1.1.1:
version "1.2.0"
resolved "https://registry.npmmirror.com/aproba/-/aproba-1.2.0.tgz#6802e6264efd18c790a1b0d517f0f2627bf2c94a"
@ -2651,6 +2798,14 @@ arch@^2.1.1:
resolved "https://registry.npmmirror.com/arch/-/arch-2.2.0.tgz#1bc47818f305764f23ab3306b0bfc086c5a29d11"
integrity sha512-Of/R0wqp83cgHozfIYLbBMnej79U/SVGOOyuB3VVFv1NRM/PSFMK12x9KVtiYzJqmnU5WR2qp0Z5rHb7sWGnFQ==
are-we-there-yet@^2.0.0:
version "2.0.0"
resolved "https://registry.npmmirror.com/are-we-there-yet/-/are-we-there-yet-2.0.0.tgz#372e0e7bd279d8e94c653aaa1f67200884bf3e1c"
integrity sha512-Ci/qENmwHnsYo9xKIcUJN5LeDKdJ6R1Z1j9V/J5wyq8nh/mYPEpIKJbBZXtZjG04HiK7zV/p6Vs9952MrMeUIw==
dependencies:
delegates "^1.0.0"
readable-stream "^3.6.0"
argparse@^1.0.7:
version "1.0.10"
resolved "https://registry.npmmirror.com/argparse/-/argparse-1.0.10.tgz#bcd6791ea5ae09725e17e5ad988134cd40b3d911"
@ -2831,6 +2986,15 @@ babel-plugin-dynamic-import-node@^2.3.3:
dependencies:
object.assign "^4.1.0"
babel-plugin-macros@^2.6.1:
version "2.8.0"
resolved "https://registry.npmmirror.com/babel-plugin-macros/-/babel-plugin-macros-2.8.0.tgz#0f958a7cc6556b1e65344465d99111a1e5e10138"
integrity sha512-SEP5kJpfGYqYKpBrj5XU3ahw5p5GOHJ0U5ssOSQ/WBVdwkD2Dzlce95exQTs3jOVWPPKLBN2rlEWkCK7dSmLvg==
dependencies:
"@babel/runtime" "^7.7.2"
cosmiconfig "^6.0.0"
resolve "^1.12.0"
babel-plugin-polyfill-corejs2@^0.3.3:
version "0.3.3"
resolved "https://registry.npmmirror.com/babel-plugin-polyfill-corejs2/-/babel-plugin-polyfill-corejs2-0.3.3.tgz#5d1bd3836d0a19e1b84bbf2d9640ccb6f951c122"
@ -2855,6 +3019,15 @@ babel-plugin-polyfill-regenerator@^0.4.1:
dependencies:
"@babel/helper-define-polyfill-provider" "^0.3.3"
babel-plugin-preval@^4.0.0:
version "4.0.0"
resolved "https://registry.npmmirror.com/babel-plugin-preval/-/babel-plugin-preval-4.0.0.tgz#edb8501167985752aafcc31086791e1314052e9d"
integrity sha512-fZI/4cYneinlj2k/FsXw0/lTWSC5KKoepUueS1g25Gb5vx3GrRyaVwxWCshYqx11GEU4mZnbbFhee8vpquFS2w==
dependencies:
"@babel/runtime" "^7.7.2"
babel-plugin-macros "^2.6.1"
require-from-string "^2.0.2"
balanced-match@^1.0.0:
version "1.0.2"
resolved "https://registry.npmmirror.com/balanced-match/-/balanced-match-1.0.2.tgz#e83e3a7e3f300b34cb9d87f615fa0cbf357690ee"
@ -3645,6 +3818,11 @@ color-name@~1.1.4:
resolved "https://registry.npmmirror.com/color-name/-/color-name-1.1.4.tgz#c2a09a87acbde69543de6f63fa3995c826c536a2"
integrity sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==
color-support@^1.1.2:
version "1.1.3"
resolved "https://registry.npmmirror.com/color-support/-/color-support-1.1.3.tgz#93834379a1cc9a0c61f82f52f0d04322251bd5a2"
integrity sha512-qiBjkpbMLO/HL68y+lh4q0/O1MZFj2RX6X/KmMa3+gJD3z+WwI1ZzDHysvqHGS3mP6mznPckpXmw1nI9cJjyRg==
colord@^2.9.1:
version "2.9.3"
resolved "https://registry.npmmirror.com/colord/-/colord-2.9.3.tgz#4f8ce919de456f1d5c1c368c307fe20f3e59fb43"
@ -3694,6 +3872,13 @@ commander@^8.3.0:
resolved "https://registry.npmmirror.com/commander/-/commander-8.3.0.tgz#4837ea1b2da67b9c616a67afbb0fafee567bca66"
integrity sha512-OkTL9umf+He2DZkUq8f8J9of7yL6RJKI24dVITBmNfZBmri9zYZQrKkuXiKhyfPSu8tUhnVBB1iKXevvnlR4Ww==
commander@~1.1.1:
version "1.1.1"
resolved "https://registry.npmmirror.com/commander/-/commander-1.1.1.tgz#50d1651868ae60eccff0a2d9f34595376bc6b041"
integrity sha512-71Rod2AhcH3JhkBikVpNd0pA+fWsmAaVoti6OR38T76chA7vE3pSerS0Jor4wDw+tOueD2zLVvFOw5H0Rcj7rA==
dependencies:
keypress "0.1.x"
common-tags@^1.8.0:
version "1.8.2"
resolved "https://registry.npmmirror.com/common-tags/-/common-tags-1.8.2.tgz#94ebb3c076d26032745fd54face7f688ef5ac9c6"
@ -3795,6 +3980,11 @@ console-browserify@^1.1.0:
resolved "https://registry.npmmirror.com/console-browserify/-/console-browserify-1.2.0.tgz#67063cef57ceb6cf4993a2ab3a55840ae8c49336"
integrity sha512-ZMkYO/LkF17QvCPqM0gxw8yUzigAOZOSWSHg91FH6orS7vcEj5dVZTidN2fQ14yBSdg97RqhSNwLUXInd52OTA==
console-control-strings@^1.0.0, console-control-strings@^1.1.0:
version "1.1.0"
resolved "https://registry.npmmirror.com/console-control-strings/-/console-control-strings-1.1.0.tgz#3d7cf4464db6446ea644bf4b39507f9851008e8e"
integrity sha512-ty/fTekppD2fIwRvnZAVdeOiGd1c7YXEixbgJTNzqcxJWKQnjJ/V1bNEEE6hygpM3WjwHFUVK6HTjWSzV4a8sQ==
consolidate@^0.15.1:
version "0.15.1"
resolved "https://registry.npmmirror.com/consolidate/-/consolidate-0.15.1.tgz#21ab043235c71a07d45d9aad98593b0dba56bab7"
@ -4282,6 +4472,11 @@ delegate@^3.1.2:
resolved "https://registry.yarnpkg.com/delegate/-/delegate-3.2.0.tgz#b66b71c3158522e8ab5744f720d8ca0c2af59166"
integrity sha512-IofjkYBZaZivn0V8nnsMJGBr4jVLxHDheKSW88PyxS5QC4Vo9ZbZVvhzlSxY87fVq3STR6r+4cGepyHkcWOQSw==
delegates@^1.0.0:
version "1.0.0"
resolved "https://registry.npmmirror.com/delegates/-/delegates-1.0.0.tgz#84c6e159b81904fdca59a0ef44cd870d31250f9a"
integrity sha512-bd2L678uiWATM6m5Z1VzNCErI3jiGzt6HGY8OVICs40JQq/HALfbyNJmp0UDakEY4pMMaN0Ly5om/B1VI/+xfQ==
depd@2.0.0:
version "2.0.0"
resolved "https://registry.npmmirror.com/depd/-/depd-2.0.0.tgz#b696163cc757560d09cf22cc8fad1571b79e76df"
@ -4310,6 +4505,11 @@ detect-browser@^5.3.0:
resolved "https://registry.npmmirror.com/detect-browser/-/detect-browser-5.3.0.tgz#9705ef2bddf46072d0f7265a1fe300e36fe7ceca"
integrity sha512-53rsFbGdwMwlF7qvCt0ypLM5V5/Mbl0szB7GPN8y9NCcbknYOeVVXdrXEq+90IwAfrrzt6Hd+u2E2ntakICU8w==
detect-libc@^2.0.0:
version "2.0.1"
resolved "https://registry.npmmirror.com/detect-libc/-/detect-libc-2.0.1.tgz#e1897aa88fa6ad197862937fbc0441ef352ee0cd"
integrity sha512-463v3ZeIrcWtdgIg6vI6XUncguvr2TnGl4SzDXinkt9mSLpBJKXT3mW6xT3VQdDN11+WVs29pgvivTc4Lp8v+w==
detect-node@^2.0.4:
version "2.1.0"
resolved "https://registry.npmmirror.com/detect-node/-/detect-node-2.1.0.tgz#c9c70775a49c3d03bc2c06d9a73be550f978f8b1"
@ -5511,6 +5711,21 @@ functions-have-names@^1.2.2:
resolved "https://registry.npmmirror.com/functions-have-names/-/functions-have-names-1.2.3.tgz#0404fe4ee2ba2f607f0e0ec3c80bae994133b834"
integrity sha512-xckBUXyTIqT97tq2x2AMb+g163b5JFysYk0x4qxNFwbfQkmNZoiRHb6sPzI9/QV33WeuvVYBUIiD4NzNIyqaRQ==
gauge@^3.0.0:
version "3.0.2"
resolved "https://registry.npmmirror.com/gauge/-/gauge-3.0.2.tgz#03bf4441c044383908bcfa0656ad91803259b395"
integrity sha512-+5J6MS/5XksCuXq++uFRsnUd7Ovu1XenbeuIuNRJxYWjgQbPuFhT14lAvsWfqfAmnwluf1OwMjz39HjfLPci0Q==
dependencies:
aproba "^1.0.3 || ^2.0.0"
color-support "^1.1.2"
console-control-strings "^1.0.0"
has-unicode "^2.0.1"
object-assign "^4.1.1"
signal-exit "^3.0.0"
string-width "^4.2.3"
strip-ansi "^6.0.1"
wide-align "^1.1.2"
gensync@^1.0.0-beta.2:
version "1.0.0-beta.2"
resolved "https://registry.npmmirror.com/gensync/-/gensync-1.0.0-beta.2.tgz#32a6ee76c3d7f52d46b2b1ae5d93fea8580a25e0"
@ -5783,6 +5998,11 @@ has-tostringtag@^1.0.0:
dependencies:
has-symbols "^1.0.2"
has-unicode@^2.0.1:
version "2.0.1"
resolved "https://registry.npmmirror.com/has-unicode/-/has-unicode-2.0.1.tgz#e0e6fe6a28cf51138855e086d1691e771de2a8b9"
integrity sha512-8Rf9Y83NBReMnx0gFzA8JImQACstCYWUplepDa9xprwwtmgEZUF0h/i5xSA625zB/I37EtrswSST6OXxwaaIJQ==
has-value@^0.3.1:
version "0.3.1"
resolved "https://registry.npmmirror.com/has-value/-/has-value-0.3.1.tgz#7b1f58bada62ca827ec0a2078025654845995e1f"
@ -6268,6 +6488,13 @@ is-ci@^3.0.0:
dependencies:
ci-info "^3.2.0"
is-core-module@^2.11.0:
version "2.12.0"
resolved "https://registry.npmmirror.com/is-core-module/-/is-core-module-2.12.0.tgz#36ad62f6f73c8253fd6472517a12483cf03e7ec4"
integrity sha512-RECHCBCd/viahWmwj6enj19sKbHfJrddi/6cBDsNTKbNq0f7VeaUkBo60BqzvPqo/W54ChS62Z5qyun7cfOMqQ==
dependencies:
has "^1.0.3"
is-core-module@^2.9.0:
version "2.11.0"
resolved "https://registry.npmmirror.com/is-core-module/-/is-core-module-2.11.0.tgz#ad4cb3e3863e814523c96f3f58d26cc570ff0144"
@ -6774,6 +7001,11 @@ jszip@^3.1.0:
readable-stream "~2.3.6"
setimmediate "^1.0.5"
keypress@0.1.x:
version "0.1.0"
resolved "https://registry.npmmirror.com/keypress/-/keypress-0.1.0.tgz#4a3188d4291b66b4f65edb99f806aa9ae293592a"
integrity sha512-x0yf9PL/nx9Nw9oLL8ZVErFAk85/lslwEP7Vz7s5SI1ODXZIgit3C5qyWjw4DxOuO/3Hb4866SQh28a1V1d+WA==
keyv@^3.0.0:
version "3.1.0"
resolved "https://registry.npmmirror.com/keyv/-/keyv-3.1.0.tgz#ecc228486f69991e49e9476485a5be1e8fc5c4d9"
@ -7485,6 +7717,11 @@ node-addon-api@^1.6.3:
resolved "https://registry.npmmirror.com/node-addon-api/-/node-addon-api-1.7.2.tgz#3df30b95720b53c24e59948b49532b662444f54d"
integrity sha512-ibPK3iA+vaY1eEjESkQkM0BbCqFOaZMiXRTtdB0u7b4djtY6JnsjvPdUHVMg6xQt3B8fpTTWHI9A+ADjM9frzg==
node-addon-api@^3.0.2:
version "3.2.1"
resolved "https://registry.npmmirror.com/node-addon-api/-/node-addon-api-3.2.1.tgz#81325e0a2117789c0128dab65e7e38f07ceba161"
integrity sha512-mmcei9JghVNDYydghQmeDX8KoAm0FAiYyIcUt/N4nhyAipB17pllZQDOJD2fotxABnt4Mdz+dKTO7eftLg4d0A==
node-fetch@^2.6.7:
version "2.6.7"
resolved "https://registry.npmmirror.com/node-fetch/-/node-fetch-2.6.7.tgz#24de9fba827e3b4ae44dc8b20256a379160052ad"
@ -7531,6 +7768,21 @@ node-releases@^2.0.6:
resolved "https://registry.npmmirror.com/node-releases/-/node-releases-2.0.6.tgz#8a7088c63a55e493845683ebf3c828d8c51c5503"
integrity sha512-PiVXnNuFm5+iYkLBNeq5211hvO38y63T0i2KKh2KnUs3RpzJ+JtODFjkD8yjLwnDkTYF1eKXheUwdssR+NRZdg==
nodejieba@2.5.2:
version "2.5.2"
resolved "https://registry.npmmirror.com/nodejieba/-/nodejieba-2.5.2.tgz#fc929ee29f93c28c639696bac0319bac116a296a"
integrity sha512-ByskJvaBrQ2eV+5M0OeD80S5NKoGaHc9zi3Z/PTKl/95eac2YF8RmWduq9AknLpkQLrLAIcqurrtC6BzjpKwwg==
dependencies:
"@mapbox/node-pre-gyp" "^1.0.4"
node-addon-api "^3.0.2"
nopt@^5.0.0:
version "5.0.0"
resolved "https://registry.npmmirror.com/nopt/-/nopt-5.0.0.tgz#530942bb58a512fccafe53fe210f13a25355dc88"
integrity sha512-Tbj67rffqceeLpcRXrT7vKAN8CwfPeIBgM7E6iBkmKLV7bEMwpGgYLGv0jACUsECaa/vuxP0IjEont6umdMgtQ==
dependencies:
abbrev "1"
normalize-package-data@^2.5.0:
version "2.5.0"
resolved "https://registry.npmmirror.com/normalize-package-data/-/normalize-package-data-2.5.0.tgz#e66db1838b200c1dfc233225d12cb36520e234a8"
@ -7595,6 +7847,16 @@ npm-run-path@^4.0.1:
dependencies:
path-key "^3.0.0"
npmlog@^5.0.1:
version "5.0.1"
resolved "https://registry.npmmirror.com/npmlog/-/npmlog-5.0.1.tgz#f06678e80e29419ad67ab964e0fa69959c1eb8b0"
integrity sha512-AqZtDUWOMKs1G/8lwylVjrdYgqA4d9nu8hc+0gzRxlDb1I10+FHBGMXs6aiQHFdCUUlqH99MUMuLfzWDNDtfxw==
dependencies:
are-we-there-yet "^2.0.0"
console-control-strings "^1.1.0"
gauge "^3.0.0"
set-blocking "^2.0.0"
nth-check@^2.0.1:
version "2.1.1"
resolved "https://registry.npmmirror.com/nth-check/-/nth-check-2.1.1.tgz#c9eab428effce36cd6b92c924bdb000ef1f1ed1d"
@ -8007,6 +8269,17 @@ pify@^4.0.1:
resolved "https://registry.npmmirror.com/pify/-/pify-4.0.1.tgz#4b2cd25c50d598735c50292224fd8c6df41e3231"
integrity sha512-uB80kBFb/tfd68bVleG9T5GGsGPjJrLAUpR5PZIrhBnIaRTQRjqdJSsIKkOP6OAIFbj7GOrcudc5pNjZ+geV2g==
pinyin@^3.0.0-alpha.4:
version "3.0.0-alpha.4"
resolved "https://registry.npmmirror.com/pinyin/-/pinyin-3.0.0-alpha.4.tgz#117f84003f81e547fa5c390f33cc1b5423366c9c"
integrity sha512-KuuztSUK/91r8/yytH0KPhpehPAj6QzNLOUTagb1M3EviX9HvOtz5g2OghY45e7ls3W3dsdghVZ1csw7rhqz5g==
dependencies:
commander "~1.1.1"
optionalDependencies:
"@node-rs/jieba" "^1.6.0"
nodejieba "2.5.2"
segmentit "^2.0.3"
pkg-dir@^3.0.0:
version "3.0.0"
resolved "https://registry.npmmirror.com/pkg-dir/-/pkg-dir-3.0.0.tgz#2749020f239ed990881b1f71210d51eb6523bea3"
@ -8395,6 +8668,13 @@ pretty-error@^4.0.0:
lodash "^4.17.20"
renderkid "^3.0.0"
preval.macro@^4.0.0:
version "4.0.0"
resolved "https://registry.npmmirror.com/preval.macro/-/preval.macro-4.0.0.tgz#24218fa36f68bf8a01a8c65c45d19a3ccad6496c"
integrity sha512-sJJnE71X+MPr64CVD2AurmUj4JEDqbudYbStav3L9Xjcqm4AR0ymMm6sugw1mUmfI/7gw4JWA4JXo/k6w34crw==
dependencies:
babel-plugin-preval "^4.0.0"
process-nextick-args@~2.0.0:
version "2.0.1"
resolved "https://registry.npmmirror.com/process-nextick-args/-/process-nextick-args-2.0.1.tgz#7820d9b16120cc55ca9ae7792680ae7dba6d7fe2"
@ -8861,6 +9141,15 @@ resolve@^1.10.0, resolve@^1.14.2, resolve@^1.19.0:
path-parse "^1.0.7"
supports-preserve-symlinks-flag "^1.0.0"
resolve@^1.12.0:
version "1.22.2"
resolved "https://registry.npmmirror.com/resolve/-/resolve-1.22.2.tgz#0ed0943d4e301867955766c9f3e1ae6d01c6845f"
integrity sha512-Sb+mjNHOULsBv818T40qSPeRiuWLyaGMa5ewydRLFimneixmVy2zdivRl+AF6jaYPC8ERxGDmFSiqui6SfPd+g==
dependencies:
is-core-module "^2.11.0"
path-parse "^1.0.7"
supports-preserve-symlinks-flag "^1.0.0"
responselike@^1.0.2:
version "1.0.2"
resolved "https://registry.npmmirror.com/responselike/-/responselike-1.0.2.tgz#918720ef3b631c5642be068f15ade5a46f4ba1e7"
@ -9053,6 +9342,13 @@ schema-utils@^4.0.0:
ajv-formats "^2.1.1"
ajv-keywords "^5.0.0"
segmentit@^2.0.3:
version "2.0.3"
resolved "https://registry.npmmirror.com/segmentit/-/segmentit-2.0.3.tgz#799897667acbc518b27811acdb2a341a79c7973f"
integrity sha512-7mn2XL3OdTUQ+AhHz7SbgyxLTaQRzTWQNVwiK+UlTO8aePGbSwvKUzTwE4238+OUY9MoR6ksAg35zl8sfTunQQ==
dependencies:
preval.macro "^4.0.0"
select-hose@^2.0.0:
version "2.0.0"
resolved "https://registry.npmmirror.com/select-hose/-/select-hose-2.0.0.tgz#625d8658f865af43ec962bfc376a37359a4994ca"
@ -9572,15 +9868,7 @@ strict-uri-encode@^1.0.0:
resolved "https://registry.npmmirror.com/strict-uri-encode/-/strict-uri-encode-1.1.0.tgz#279b225df1d582b1f54e65addd4352e18faa0713"
integrity sha512-R3f198pcvnB+5IpnBlRkphuE9n46WyVl8I39W/ZUTZLz4nqSP/oLYUrcnJrw462Ds8he4YKMov2efsTIw1BDGQ==
string-width@^2.0.0, string-width@^2.1.1:
version "2.1.1"
resolved "https://registry.npmmirror.com/string-width/-/string-width-2.1.1.tgz#ab93f27a8dc13d28cac815c462143a6d9012ae9e"
integrity sha512-nOqH59deCq9SRHlxq1Aw85Jnt4w6KvLKqWVik6oA9ZklXLNIOlqg4F2yrT1MVaTjAqvVwdfeZ7w7aCvJD7ugkw==
dependencies:
is-fullwidth-code-point "^2.0.0"
strip-ansi "^4.0.0"
string-width@^4.0.0, string-width@^4.1.0, string-width@^4.2.0, string-width@^4.2.2, string-width@^4.2.3:
"string-width@^1.0.2 || 2 || 3 || 4", string-width@^4.0.0, string-width@^4.1.0, string-width@^4.2.0, string-width@^4.2.2, string-width@^4.2.3:
version "4.2.3"
resolved "https://registry.npmmirror.com/string-width/-/string-width-4.2.3.tgz#269c7117d27b05ad2e536830a8ec895ef9c6d010"
integrity sha512-wKyQRQpjJ0sIp62ErSZdGsjMJWsap5oRNihHhu6G7JVO/9jIB6UyevL+tXuOqrng8j/cxKTWyWUwvSTriiZz/g==
@ -9589,6 +9877,14 @@ string-width@^4.0.0, string-width@^4.1.0, string-width@^4.2.0, string-width@^4.2
is-fullwidth-code-point "^3.0.0"
strip-ansi "^6.0.1"
string-width@^2.0.0, string-width@^2.1.1:
version "2.1.1"
resolved "https://registry.npmmirror.com/string-width/-/string-width-2.1.1.tgz#ab93f27a8dc13d28cac815c462143a6d9012ae9e"
integrity sha512-nOqH59deCq9SRHlxq1Aw85Jnt4w6KvLKqWVik6oA9ZklXLNIOlqg4F2yrT1MVaTjAqvVwdfeZ7w7aCvJD7ugkw==
dependencies:
is-fullwidth-code-point "^2.0.0"
strip-ansi "^4.0.0"
string.prototype.matchall@^4.0.6:
version "4.0.8"
resolved "https://registry.npmmirror.com/string.prototype.matchall/-/string.prototype.matchall-4.0.8.tgz#3bf85722021816dcd1bf38bb714915887ca79fd3"
@ -9836,7 +10132,7 @@ tapable@^2.0.0, tapable@^2.1.1, tapable@^2.2.0:
resolved "https://registry.npmmirror.com/tapable/-/tapable-2.2.1.tgz#1967a73ef4060a82f12ab96af86d52fdb76eeca0"
integrity sha512-GNzQvQTOIP6RyTfE2Qxb8ZVlNmw0n88vp1szwWRimP02mnTsx3Wtn5qRdqY9w2XduFNUgvOwhNnQsjwCp+kqaQ==
tar@^6.0.2:
tar@^6.0.2, tar@^6.1.11:
version "6.1.13"
resolved "https://registry.npmmirror.com/tar/-/tar-6.1.13.tgz#46e22529000f612180601a6fe0680e7da508847b"
integrity sha512-jdIBIN6LTIe2jqzay/2vtYLlBHa3JF42ot3h1dW8Q0PaAG4v8rm0cvpVePtau5C6OKXGGcgO9q2AMNSWxiLqKw==
@ -10623,6 +10919,18 @@ vue-template-es2015-compiler@^1.9.0:
resolved "https://registry.npmmirror.com/vue-template-es2015-compiler/-/vue-template-es2015-compiler-1.9.1.tgz#1ee3bc9a16ecbf5118be334bb15f9c46f82f5825"
integrity sha512-4gDntzrifFnCEvyoO8PqyJDmguXgVPxKiIxrBKjIowvL9l+N66196+72XVYR8BBf1Uv1Fgt3bGevJ+sEmxfZzw==
vue3-bcui@^0.2.1:
version "0.2.1"
resolved "https://registry.yarnpkg.com/vue3-bcui/-/vue3-bcui-0.2.1.tgz#02d3ff835fd96fd4e4d110d9be0a50df2544ea03"
integrity sha512-Fih3XLCq3U6VYxP4wUzqD5sxd78Jeyz28ByYWqdK9N68gpKyWf6+W7y51WaQMEL54lvXNEs1dDyKvv5QdR51Kw==
dependencies:
"@fortawesome/fontawesome-svg-core" "^6.3.0"
"@fortawesome/free-regular-svg-icons" "^6.3.0"
"@fortawesome/free-solid-svg-icons" "^6.3.0"
"@fortawesome/vue-fontawesome" "^3.0.3"
core-js "^3.8.3"
vue "^3.2.13"
vue3-infinite-scroll-better@^2.2.0:
version "2.2.0"
resolved "https://registry.npmmirror.com/vue3-infinite-scroll-better/-/vue3-infinite-scroll-better-2.2.0.tgz#73a74df93a893fc66e44da2dabd97dbc1139054e"
@ -10916,6 +11224,13 @@ which@^2.0.1:
dependencies:
isexe "^2.0.0"
wide-align@^1.1.2:
version "1.1.5"
resolved "https://registry.npmmirror.com/wide-align/-/wide-align-1.1.5.tgz#df1d4c206854369ecf3c9a4898f1b23fbd9d15d3"
integrity sha512-eDMORYaPNZ4sQIuuYPDHdQvf4gyCF9rEEV/yPxGfwPkRodwEgiMUUXTx/dex+Me0wxx53S+NgUHaP7y3MGlDmg==
dependencies:
string-width "^1.0.2 || 2 || 3 || 4"
widest-line@^3.1.0:
version "3.1.0"
resolved "https://registry.npmmirror.com/widest-line/-/widest-line-3.1.0.tgz#8292333bbf66cb45ff0de1603b136b7ae1496eca"