feat: 项目开始重构 #17 #22

This commit is contained in:
imsyy 2023-07-27 17:33:15 +08:00
parent c2bd259140
commit be65ecdbcc
59 changed files with 1975 additions and 3700 deletions

2
.env Normal file
View File

@ -0,0 +1,2 @@
# 搜索框提示词
VITE_INPUT_TIP = "想要搜点什么"

25
.gitignore vendored
View File

@ -1 +1,24 @@
.vscode # Logs
logs
*.log
npm-debug.log*
yarn-debug.log*
yarn-error.log*
pnpm-debug.log*
lerna-debug.log*
node_modules
dist
dist-ssr
*.local
# Editor directories and files
.vscode/*
!.vscode/extensions.json
.idea
.DS_Store
*.suo
*.ntvs*
*.njsproj
*.sln
*.sw?

3
.vscode/extensions.json vendored Normal file
View File

@ -0,0 +1,3 @@
{
"recommendations": ["Vue.volar", "Vue.vscode-typescript-vue-plugin"]
}

View File

@ -5,12 +5,13 @@
![Snavigation.png](https://s2.loli.net/2022/07/15/FE6U2BJCynHDep8.jpg) ![Snavigation.png](https://s2.loli.net/2022/07/15/FE6U2BJCynHDep8.jpg)
>尚未完成 > 重构中,尚未完成
### Demo ### Demo
>由于 CDN 缓存原因,查看最新效果可能需要 `Ctrl` + `F5` 强制刷新浏览器缓存 > 由于 `CDN` 缓存原因,查看最新效果可能需要 `Ctrl` + `F5` 强制刷新浏览器缓存
- [Snavigation](https://snavigation.vercel.app/) - [Snavigation](https://nav.imsyy.top)
- [Snavigation Dev](https://snavigation.vercel.app)
### 功能 ### 功能
@ -23,22 +24,50 @@
- [x] 移动端适配 - [x] 移动端适配
* [ ] 还没想好呢 * [ ] 还没想好呢
### 插件 ### 部署
* [iziToast](https://izitoast.marcelodolza.com/) * **安装** [node.js](https://nodejs.org/zh-cn/) **环境**
* [Iconfont](https://www.iconfont.cn/)
* [jQuery](https://jquery.com/) > node > 16.16.0
> npm > 8.15.0
* 然后以 **管理员权限** 运行 `cmd` 终端,并 `cd` 到 项目根目录
* 在 `终端` 中输入:
```bash
# 安装 pnpm
npm install -g pnpm
# 安装依赖
pnpm install
# 开发
pnpm dev
# 构建
pnpm build
```
> 构建完成后,静态资源会在 **`dist` 目录** 中生成,可将 **`dist` 文件夹下的文件**上传至服务器,
> 也可使用 [Vercel](https://vercel.com/) 或 [Cloudflare Pages](https://pages.cloudflare.com/) 等托管平台一键自动部署
### 技术栈
* [Vue](https://cn.vuejs.org/)
* [Vite](https://vitejs.cn/vite3-cn/)
* [Pinia](https://pinia.vuejs.org/zh/)
* [iconfont](https://www.iconfont.cn/)
### API ### API
* [小歪 API](https://api.ixiaowai.cn/) * [小歪 API](https://api.ixiaowai.cn/)
* [天气 API](https://www.tianqiapi.com/) * [缙哥哥 API](https://www.dujin.org/3618.html)
* [Hitokoto 一言](https://hitokoto.cn/)
### 鸣谢 ### 鸣谢
本站部分内容参考自 本站部分样式及功能参考自
* [青柠起始页](https://limestart.cn/) * [青柠起始页](https://limestart.cn/)
* [sou2](https://github.com/yeetime/sou2/)
<a title="SSL" target="_blank" href="https://myssl.com/seal/detail?domain=blog.imsyy.top"><img src="https://img.shields.io/badge/MySSL-安全认证-brightgreen"></a>&nbsp;<a title="CDN" target="_blank" href="https://cdnjs.com/"><img src="https://img.shields.io/badge/CDN-Cloudflare-blue"></a>&nbsp;<a title="Copyright" target="_blank" href="https://imsyy.top/"><img src="https://img.shields.io/badge/Copyright%20%C2%A9%202020--2022-%E7%84%A1%E5%90%8D-red"></a> <a title="SSL" target="_blank" href="https://myssl.com/seal/detail?domain=blog.imsyy.top"><img src="https://img.shields.io/badge/MySSL-安全认证-brightgreen"></a>&nbsp;<a title="CDN" target="_blank" href="https://cdnjs.com/"><img src="https://img.shields.io/badge/CDN-Cloudflare-blue"></a>&nbsp;<a title="Copyright" target="_blank" href="https://imsyy.top/"><img src="https://img.shields.io/badge/Copyright%20%C2%A9%202020--2022-%E7%84%A1%E5%90%8D-red"></a>

View File

@ -1,202 +0,0 @@
/*渐入动画*/
@keyframes fade {
0% {
opacity: 0;
}
100% {
opacity: 1;
}
}
@-webkit-keyframes fade {
0% {
opacity: 0;
}
100% {
opacity: 1;
}
}
@-moz-keyframes fade {
0% {
opacity: 0;
}
100% {
opacity: 1;
}
}
@-o-keyframes fade {
0% {
opacity: 0;
}
100% {
opacity: 1;
}
}
/*文字闪烁*/
@-webkit-keyframes fadenum {
0% {
opacity: 1;
}
50% {
opacity: 0;
}
100% {
opacity: 1;
}
}
@-moz-keyframes fadenum {
0% {
opacity: 1;
}
50% {
opacity: 0;
}
100% {
opacity: 1;
}
}
@-o-keyframes fadenum {
0% {
opacity: 1;
}
50% {
opacity: 0;
}
100% {
opacity: 1;
}
}
@keyframes fadenum {
0% {
opacity: 1;
}
50% {
opacity: 0;
}
100% {
opacity: 1;
}
}
/*下沉动画*/
@-moz-keyframes down {
0% {
opacity: 0;
top: 44%;
/* -webkit-transform: translateY(-25%);
-moz-transform: translateY(-25%);
-o-transform: translateY(-25%);
-ms-transform: translateY(-25%);
transform: translateY(-25%) */
}
100% {
opacity: 1;
-ms-filter: none;
filter: none;
top: 46%;
/* -webkit-transform: translateY(-20%);
-moz-transform: translateY(-20%);
-o-transform: translateY(-20%);
-ms-transform: translateY(-20%);
transform: translateY(-20%) */
}
}
@-webkit-keyframes down {
0% {
opacity: 0;
top: 44%;
/* -webkit-transform: translateY(-25%);
-moz-transform: translateY(-25%);
-o-transform: translateY(-25%);
-ms-transform: translateY(-25%);
transform: translateY(-25%) */
}
100% {
opacity: 1;
-ms-filter: none;
filter: none;
top: 46%;
/* -webkit-transform: translateY(-20%);
-moz-transform: translateY(-20%);
-o-transform: translateY(-20%);
-ms-transform: translateY(-20%);
transform: translateY(-20%) */
}
}
@-o-keyframes down {
0% {
opacity: 0;
top: 44%;
/* -webkit-transform: translateY(-25%);
-moz-transform: translateY(-25%);
-o-transform: translateY(-25%);
-ms-transform: translateY(-25%);
transform: translateY(-25%) */
}
100% {
opacity: 1;
-ms-filter: none;
filter: none;
top: 46%;
/* -webkit-transform: translateY(-20%);
-moz-transform: translateY(-20%);
-o-transform: translateY(-20%);
-ms-transform: translateY(-20%);
transform: translateY(-20%) */
}
}
@keyframes down {
0% {
opacity: 0;
top: 44%;
/* -webkit-transform: translateY(-25%);
-moz-transform: translateY(-25%);
-o-transform: translateY(-25%);
-ms-transform: translateY(-25%);
transform: translateY(-25%) */
}
100% {
opacity: 1;
-ms-filter: none;
filter: none;
top: 46%;
/* -webkit-transform: translateY(-20%);
-moz-transform: translateY(-20%);
-o-transform: translateY(-20%);
-ms-transform: translateY(-20%);
transform: translateY(-20%) */
}
}

View File

@ -1,92 +0,0 @@
@font-face {
font-family: "MiSans";
src: url('../font/MiSans-Regular.subset.woff2') format('woff');
}
@font-face {
font-family: "iconfont";
/* Project id 3222465 */
src: url('../font/iconfont.woff2') format('woff2'),
url('../font/iconfont.woff') format('woff'),
url('../font/iconfont.ttf') format('truetype');
}
.iconfont {
font-family: "iconfont" !important;
font-size: 16px;
font-style: normal;
-webkit-font-smoothing: antialiased;
-moz-osx-font-smoothing: grayscale;
}
.icon-tianjia-:before {
content: "\e643";
}
.icon-taobao:before {
content: "\e755";
}
.icon-jingdong:before {
content: "\e618";
}
.icon-xinlangweibo:before {
content: "\e601";
}
.icon-zhihu:before {
content: "\e60a";
}
.icon-github:before {
content: "\e691";
}
.icon-delete:before {
content: "\e94d";
}
.icon-home:before {
content: "\e964";
}
.icon-xiugai:before {
content: "\e626";
}
.icon-bilibilidonghua:before {
content: "\e8b1";
}
.icon-wangluo:before {
content: "\e600";
}
.icon-sougousousuo:before {
content: "\e685";
}
.icon-360sousuo:before {
content: "\e64d";
}
.icon-baidu:before {
content: "\eb49";
}
.icon-bing:before {
content: "\eb4c";
}
.icon-google:before {
content: "\ebaa";
}
.icon-shezhi:before {
content: "\e634";
}
.icon-sousuo:before {
content: "\e635";
}

View File

@ -1,127 +0,0 @@
@charset "utf-8";
#loading-box .loading-left-bg,
#loading-box .loading-right-bg {
position: fixed;
z-index: 999998;
width: 50%;
height: 100%;
background-color: rgb(81 81 81 / 80%);
transition: all 0.7s cubic-bezier(0.42, 0, 0, 1.01);
backdrop-filter: blur(10px);
}
#loading-box .loading-right-bg {
right: 0;
}
#loading-box>.spinner-box {
position: fixed;
z-index: 999999;
display: flex;
justify-content: center;
align-items: center;
width: 100%;
height: 100vh;
}
#loading-box .spinner-box .loading-word {
position: absolute;
color: #ffffff;
font-size: 0.95rem;
transform: translateY(64px);
text-align: center;
}
p.loading-title {
font-size: 1.25rem;
margin: 20px 10px 4px 10px;
}
#loading-box .spinner-box .configure-core {
width: 100%;
height: 100%;
background-color: #37474f;
}
div.loaded div.loading-left-bg {
transform: translate(-100%, 0);
}
div.loaded div.loading-right-bg {
transform: translate(100%, 0);
}
div.loaded div.spinner-box {
display: none !important;
}
.loader {
position: absolute;
top: calc(50% - 32px);
left: calc(50% - 32px);
width: 64px;
height: 64px;
border-radius: 50%;
perspective: 800px;
transition: all 0.7s cubic-bezier(0.42, 0, 0, 1.01);
}
.inner {
position: absolute;
box-sizing: border-box;
width: 100%;
height: 100%;
border-radius: 50%;
}
.inner.one {
left: 0%;
top: 0%;
animation: rotate-one 1s linear infinite;
border-bottom: 3px solid #EFEFFA;
}
.inner.two {
right: 0%;
top: 0%;
animation: rotate-two 1s linear infinite;
border-right: 3px solid #EFEFFA;
}
.inner.three {
right: 0%;
bottom: 0%;
animation: rotate-three 1s linear infinite;
border-top: 3px solid #EFEFFA;
}
@keyframes rotate-one {
0% {
transform: rotateX(35deg) rotateY(-45deg) rotateZ(0deg);
}
100% {
transform: rotateX(35deg) rotateY(-45deg) rotateZ(360deg);
}
}
@keyframes rotate-two {
0% {
transform: rotateX(50deg) rotateY(10deg) rotateZ(0deg);
}
100% {
transform: rotateX(50deg) rotateY(10deg) rotateZ(360deg);
}
}
@keyframes rotate-three {
0% {
transform: rotateX(35deg) rotateY(55deg) rotateZ(0deg);
}
100% {
transform: rotateX(35deg) rotateY(55deg) rotateZ(360deg);
}
}

View File

@ -1,94 +0,0 @@
@charset "utf-8";
/*小于1200px时*/
@media (max-width: 1200px) {
/*书签及设置高度*/
.mark,
.set {
margin-top: 180px;
}
}
/*小于720px时*/
@media (max-width: 720px) {
/*书签*/
.quick,
.quicks {
width: 23%;
min-width: 23%;
max-width: 23%;
}
}
/*小于512px时*/
@media (max-width: 512px) {
/*文字大小*/
#time_text {
font-size: 2.75rem;
}
#day {
font-size: 1.05rem;
}
.weather {
font-size: 1rem;
}
.wd::-webkit-input-placeholder {
letter-spacing: 1px;
font-size: 0.95rem;
}
/*搜索引擎*/
.se-li {
width: 31.33%;
min-width: 31.33%;
max-width: 31.33%;
}
/*设置按钮*/
#menu i {
font-size: 1.45rem;
}
/*书签*/
.quick,
.quicks {
width: 31.33%;
min-width: 31.33%;
max-width: 31.33%;
}
/*壁纸设置*/
#wallpaper {
flex-wrap: wrap;
}
#wallpaper_text {
margin-top: 0px;
}
.form-radio {
margin: 0px 10px 30px 0px;
}
/*隐藏*/
.mobile {
display: none;
}
}
/* 大于568px时 */
@media (min-width: 568px) {
.iziToast {
border-radius: 30px !important;
}
.iziToast-wrapper {
padding: 10px 0px !important;
}
}

File diff suppressed because it is too large Load Diff

Binary file not shown.

Before

Width:  |  Height:  |  Size: 17 KiB

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Before

Width:  |  Height:  |  Size: 75 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 63 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 136 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 65 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 227 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 215 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 42 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 58 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 151 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 106 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 9.4 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 654 B

View File

@ -1,562 +1,26 @@
<!DOCTYPE html> <!doctype html>
<html lang="zh"> <html lang="zh-CN">
<head>
<head> <meta charset="UTF-8" />
<meta charset="UTF-8"> <link rel="icon" type="image/svg+xml" href="favicon.png" />
<meta http-equiv="X-UA-Compatible" content="IE=edge"> <meta name="viewport" content="width=device-width, initial-scale=1.0" />
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Snavigation</title> <title>Snavigation</title>
<link rel="icon" href="favicon.ico"> <!-- HarmonyOS Sans -->
<!-- jQuery --> <link rel="stylesheet" href="https://s1.hdslb.com/bfs/static/jinkela/long/font/regular.css" />
<script src="https://lf26-cdn-tos.bytecdntp.com/cdn/expire-1-y/jquery/3.6.0/jquery.min.js"></script>
<!-- 引入样式 -->
<link rel="stylesheet" type="text/css" href="./css/style.css">
<link rel="stylesheet" type="text/css" href="./css/font.css">
<link rel="stylesheet" type="text/css" href="./css/loading.css">
<link rel="stylesheet" type="text/css" href="./css/mobile.css">
<link rel="stylesheet" type="text/css" href="./css/animation.css">
<!-- Izitoast -->
<link rel="stylesheet" href="https://lf3-cdn-tos.bytecdntp.com/cdn/expire-1-y/izitoast/1.4.0/css/iziToast.min.css">
<script type="text/javascript"
src="https://lf26-cdn-tos.bytecdntp.com/cdn/expire-1-y/izitoast/1.4.0/js/iziToast.min.js">
</script>
<!-- IE Out --> <!-- IE Out -->
<script> <script>
if ( /*@cc_on!@*/ false || (!!window.MSInputMethodContext && !!document.documentMode)) window.location.href = if (
"https://www.imsyy.top/upgrade-your-browser/index.html?referrer=" + encodeURIComponent(window.location /*@cc_on!@*/
.href); false ||
(!!window.MSInputMethodContext && !!document.documentMode)
)
window.location.href =
"https://support.dmeng.net/upgrade-your-browser.html?referrer=" +
encodeURIComponent(window.location.href);
</script> </script>
</head> </head>
<body>
<body> <div id="app"></div>
<!--加载动画--> <script type="module" src="/src/main.js"></script>
<div id="loading-box"> </body>
<div class="loading-left-bg"></div>
<div class="loading-right-bg"></div>
<div class="spinner-box">
<div class="loader">
<div class="inner one"></div>
<div class="inner two"></div>
<div class="inner three"></div>
</div>
<div class="loading-word">
<p class="loading-title">Snavigation</p>
<span id="loading-text">加载中</span>
</div>
</div>
</div>
<!-- 背景图片 -->
<div class="bg-all">
<img id="bg" onerror="this.classList.add('error');"></img>
<div class="cover"></div>
</div>
<!-- 主体内容 -->
<section id="section" class="section">
<div id="content">
<div class="con">
<!-- 时间天气 -->
<div class="tool-all">
<div class="time">
<span id="time_text">00<span id="point">:</span>00</span>
<span id="day">0&nbsp;&nbsp;00&nbsp;&nbsp;周一</span>
</div>
<div class="weather">
<span id="wea_text">N/A</span>&nbsp;<span id="tem2">N/A</span>°C&nbsp;~&nbsp;<span
id="tem1">N/A</span>°C
</div>
</div>
<!-- 搜索框 -->
<div class="close_sou"></div>
<div class="sou">
<form class="search" action="https://www.baidu.com/s" target="_Blank">
<div class="all-search">
<div class="se" title="点击切换搜索引擎">
<i id="icon-se" class="iconfont icon-baidu"></i>
</div>
<input class="wd" type="text" name="wd" placeholder="想要搜点什么" autocomplete="off">
<div class="sou-button">
<div class="s" id="s-button">
<i id="icon-sou" class="iconfont icon-sousuo"></i>
</div>
</div>
</div>
<input type="submit" id="search-submit" style="display: none;">
</form>
<div id="keywords" style="display: none;"></div>
<div class="search-engine" style="display: none;">
<div class="search-engine-list">
<div class="se-li">
<a class="se-li-text" data-url="https://www.baidu.com/s" data-name="wd"
data-icon="iconfont icon-baidu">
<i id="icon-sou-list" class="iconfont icon-sousuo"></i>
<span>百度</span>
</a>
</div>
<div class="se-li" data-url="https://cn.bing.com/search" data-name="q"
data-icon="iconfont icon-bing">
<a class="se-li-text">
<i id="icon-sou-list" class="iconfont icon-bing"></i>
<span>必应</span>
</a>
</div>
<div class="se-li" data-url="https://www.google.com/search" data-name="q"
data-icon="iconfont icon-google">
<a class="se-li-text">
<i id="icon-sou-list" class="iconfont icon-google"></i>
<span>谷歌</span>
</a>
</div>
<div class="se-li" data-url="https://www.sogou.com/web" data-name="query"
data-icon="iconfont icon-bing">
<a class="se-li-text">
<i id="icon-sou-list" class="iconfont icon-sougousousuo"></i>
<span>搜狗</span>
</a>
</div>
</div>
</div>
</div>
<!-- 书签页 -->
<div class="mark" style="display: none;">
<div class="tab">
<div class="tab-item active">常用</div>
<div class="tab-item">工具</div>
<div class="tab-item">开发</div>
<div class="tab-item">娱乐</div>
<div class="tab-item">学习</div>
<div class="tab-item">设计</div>
</div>
<div class="content products">
<!-- 常用 -->
<div class="mainCont selected">
<div class="quick-all">
<div class="quick">
<a href="https://github.com/" target="_blank">
GitHub
</a>
</div>
</div>
</div>
<!-- 开发 -->
<div class="mainCont">
<div class="quick-alls">
<div class="quicks">
<a href="https://tool.chinaz.com/" target="_blank">
站长之家
</a>
</div>
<div class="quicks">
<a href="https://www.toolnb.com/" target="_blank">
爱资料工具
</a>
</div>
<div class="quicks">
<a href="https://www.aconvert.com/cn/" target="_blank">
Aconvert
</a>
</div>
<div class="quicks">
<a href="https://next.itellyou.cn/" target="_blank">
MSDN
</a>
</div>
<div class="quicks">
<a href="https://www.bejson.com/" target="_blank">
BEJSON
</a>
</div>
<div class="quicks">
<a href="https://zh.z-lib.org/" target="_blank">
Z-Library
</a>
</div>
<div class="quicks">
<a href="https://ebook.huzerui.com/" target="_blank">
熊猫搜书
</a>
</div>
<div class="quicks">
<a href="https://vocalremover.org/ch/" target="_blank">
VocalreMover
</a>
</div>
<div class="quicks">
<a href="https://tiomg.org/" target="_blank">
太美工具
</a>
</div>
<div class="quicks">
<a href="https://s.threatbook.cn/" target="_blank">
微步云沙箱
</a>
</div>
<div class="quicks">
<a href="https://www.tablesgenerator.com/" target="_blank">
表格生成
</a>
</div>
<div class="quicks">
<a href="https://write.imsyy.top/" target="_blank">
MD 编辑器
</a>
</div>
<div class="quicks">
<a href="https://vocalremover.org/ch/" target="_blank">
VocalreMover
</a>
</div>
</div>
</div>
<!-- 工具 -->
<div class="mainCont">
<div class="quick-alls">
<div class="quicks" data-s="bilibili" title="哔哩哔哩 (゜-゜)つロ 干杯~">
<a href="https://www.bilibili.com/" target="_blank">
哔哩哔哩
</a>
</div>
<div class="quicks" data-s="github" title="GitHub">
<a href="https://github.com/" target="_blank">
GitHub
</a>
</div>
<div class="quicks" data-s="v2ex" title="V2EX">
<a href="https://www.v2ex.com/" target="_blank">
V2EX
</a>
</div>
<div class="quicks" data-s="steam" title="Steam">
<a href="https://store.steampowered.com/" target="_blank">
Steam
</a>
</div>
</div>
</div>
<!-- 娱乐 -->
<div class="mainCont">
<div class="quick-alls">
<div class="quicks" data-s="bilibili" title="哔哩哔哩 (゜-゜)つロ 干杯~">
<a href="https://www.bilibili.com/" target="_blank">
哔哩哔哩
</a>
</div>
<div class="quicks" data-s="github" title="GitHub">
<a href="https://github.com/" target="_blank">
GitHub
</a>
</div>
</div>
</div>
<!-- 学习 -->
<div class="mainCont">
<div class="quick-alls">
<div class="quicks" data-s="bilibili" title="哔哩哔哩 (゜-゜)つロ 干杯~">
<a href="https://www.bilibili.com/" target="_blank">
哔哩哔哩
</a>
</div>
<div class="quicks" data-s="github" title="GitHub">
<a href="https://github.com/" target="_blank">
GitHub
</a>
</div>
</div>
</div>
<!-- 设计 -->
<div class="mainCont">
<div class="quick-alls">
<div class="quicks" data-s="bilibili" title="哔哩哔哩 (゜-゜)つロ 干杯~">
<a href="https://www.bilibili.com/" target="_blank">
哔哩哔哩
</a>
</div>
<div class="quicks" data-s="github" title="GitHub">
<a href="https://github.com/" target="_blank">
GitHub
</a>
</div>
</div>
</div>
</div>
</div>
<!-- 设置图标 -->
<div id="menu">
<i id="icon-menu" class="iconfont icon-shezhi"></i>
</div>
<!-- 设置页 -->
<div class="set" style="display: none;">
<div class="tabs">
<div class="tab-items actives">搜索引擎</div>
<div class="tab-items" id="set-quick-menu">快捷方式</div>
<div class="tab-items">背景图片</div>
<div class="tab-items">数据备份</div>
</div>
<div class="contents productss">
<!-- 搜索引擎设置 -->
<div class="mainConts selected">
<div class="set_blocks">
<div class="set_blocks_content">
<div class="se_list">
<div class="se_list_table">
<div class="se_list_div">
<div class="se_list_num">
<i class="iconfont icon-home"></i>
</div>
<div class="se_list_name">百度</div>
<div class="se_list_button">
<button class="set_se_default" value="baidu"
style="border-radius: 8px 0px 0px 8px;">
<span class="iconfont icon-home"></span>
</button>
<button class="edit_se" value="baidu">
<span class="iconfont icon-xiugai"></span>
</button>
<button class="delete_se" value="baidu"
style="border-radius: 0px 8px 8px 0px;">
<span class="iconfont icon-delete"></span>
</button>
</div>
</div>
<div class="se_list_div">
<div class="se_list_num">2</div>
<div class="se_list_name">谷歌</div>
<div class="se_list_button">
<button class="set_se_default" value="google"><span
class="iconfont icon-home"></span></button>
<button class="edit_se" value="google"><span
class="iconfont icon-xiugai"></span></button>
<button class="delete_se" value="google"><span
class="iconfont icon-delete"></span></button>
</div>
</div>
</div>
</div>
<div class="se_add_preinstall">
<div class="set_se_list_add">
<span class="set_quick_text">新增</span>
</div>
<div class="set_se_list_preinstall">
<span class="set_quick_text">重置</span>
</div>
</div>
<div class="add_content se_add_content" style="display:none;">
<div class="froms">
<div class="from_items">
<div class="from_text">顺序</div>
<input type="hidden" name="key_inhere">
<input type="number" name="key" placeholder="请填入小于 20 的正整数"
autocomplete="off"
oninput="if(value>20)value=20;if(value<0)value=0">
</div>
<div class="from_items">
<div class="from_text">名称</div>
<input type="text" name="title" placeholder="搜索引擎名称" autocomplete="off">
</div>
<div class="from_items">
<div class="from_text">网址</div>
<input type="url" name="url" placeholder="以 https 或 http 开头的 URL"
autocomplete="off">
</div>
<div class="from_items">
<div class="from_text">字段名</div>
<input type="text" name="name" placeholder="URL 中 ? 后面的字段"
autocomplete="off">
</div>
<div class="from_items" style="display: none;">
<input type="text" name="icon" placeholder="iconfont icon-Earth"
value="iconfont icon-Earth" disabled="disabled">
</div>
</div>
<div class="from_items button">
<div class="se_add_save">保存</div>
<div class="se_add_cancel">取消</div>
</div>
</div>
</div>
</div>
</div>
<!-- 快捷方式设置 -->
<div class="mainConts">
<div class="set_blocks">
<div class="set_blocks_content">
<div class="quick_list">
<div class="quick_list_table">
<div class="quick_list_div">
<div class="quick_list_div_num">1</div>
<div class="quick_list_div_name">哔哩哔哩</div>
<div class="quick_list_div_button">
<div class="edit_quick" value="1">
<span class="iconfont iconbook-edit"></span>
</div>
<div class="delete_quick" value="1">
<span class="iconfont icondelete"></span>
</div>
</div>
</div>
<div class="quick_list_div">
<div class="quick_list_div_num">2</div>
<div class="quick_list_div_name">知乎</div>
<div class="quick_list_div_button">
<button class="edit_quick" value="2"
style="border-radius: 8px 0px 0px 8px;">
<span class="iconfont iconbook-edit"></span>
</button>
<button class="delete_quick" value="2"
style="border-radius: 0px 8px 8px 0px;">
<span class="iconfont icondelete"></span>
</button>
</div>
</div>
</div>
</div>
<div class="se_add_preinstalls">
<div class="set_quick_list_add">
<span class="set_quick_text">新增</span>
</div>
<div class="set_quick_list_preinstall">
<span class="set_quick_text">重置</span>
</div>
</div>
<div class="add_content quick_add_content" style="display:none;">
<div class="froms">
<div class="from_items">
<div class="from_text">顺序</div>
<input type="hidden" name="key_inhere">
<input type="number" name="key" placeholder="请填入小于 100 的正整数"
autocomplete="off"
oninput="if(value>99)value=99;if(value<0)value=0">
</div>
<div class="from_items">
<div class="from_text">名称</div>
<input type="text" name="title" placeholder="网站名称" autocomplete="off">
</div>
<div class="from_items">
<div class="from_text">网址</div>
<input type="url" name="url" placeholder="以 https 或 http 开头的 URL"
autocomplete="off">
</div>
</div>
<div class="from_items button">
<div class="quick_add_save">保存</div>
<div class="quick_add_cancel">取消</div>
</div>
</div>
</div>
</div>
</div>
<!-- 背景图片设置 -->
<div class="mainConts">
<div class="set_blocks">
<div class="set_tip">
<span class="set_text mobile">点击下方选项以切换壁纸,使用除默认壁纸以外的选项可能会导致页面载入缓慢</span>
<span class="set_text mobile">不建议使用以主色调为白色的壁纸,会导致本站部分元素无法辨认</span>
<span class="set_text" id="wallpaper_text">请点击选项以查看各项说明,高亮项为选中,选中后刷新页面以生效</span>
</div>
<div class="set_blocks_content">
<div class="from_container">
<div class="froms">
<div class="from_row">
<div class="from_row_content">
<div id="wallpaper">
<div class="form-radio">
<input type="radio" id="radio1" class="set-wallpaper"
name="wallpaper-type" value="1" style="display: none;">
<label class="form-radio-label" for="radio1">
默认壁纸
</label>
</div>
<div class="form-radio">
<input type="radio" id="radio2" class="set-wallpaper"
name="wallpaper-type" value="2" style="display: none;">
<label class="form-radio-label" for="radio2">
每日必应
</label>
</div>
<div class="form-radio">
<input type="radio" id="radio3" class="set-wallpaper"
name="wallpaper-type" value="3" style="display: none;">
<label class="form-radio-label" for="radio3">
随机风景
</label>
</div>
<div class="form-radio">
<input type="radio" id="radio4" class="set-wallpaper"
name="wallpaper-type" value="4" style="display: none;">
<label class="form-radio-label" for="radio4">
随机二次元
</label>
</div>
<div class="form-radio mobile">
<input type="radio" id="radio5"
class="set-wallpaper wallpaper-custom"
name="wallpaper-type" value="5" style="display: none;">
<label class="form-radio-label" for="radio5">
自定义壁纸
</label>
</div>
</div>
</div>
</div>
<div id="wallpaper_url" style="display: none;">
<div class="from_row">
<div class="from_items">
<input type="text" name="wallpaper-url" id="wallpaper-url"
placeholder="以 https 或 http 开头的 URL" autocomplete="off">
</div>
</div>
</div>
</div>
</div>
<div class="from_items button" id="wallpaper-button" style="display: none;">
<div class="wallpaper_save">保存</div>
</div>
</div>
</div>
</div>
<!-- 数据备份设置 -->
<div class="mainConts">
<div class="set_blocks">
<div class="set_tip">
<span class="set_text">点击导出会将本站文件导出至下载目录</span>
<span class="set_text">点击导入可选择已备份文件进行恢复</span>
<span class="set_text">本功能尚未完善,若遇到问题可在设置进行重置</span>
</div>
<div class="set_button">
<div class="but-ordinary" id="my_data_in">导入</div>
<div class="but-ordinary" id="my_data_out">导出</div>
<input type="file" id="my_data_file" name="file" style="display: none">
</div>
<div class="set_version">
<span class="set_version-text">MADE&nbsp;BY&nbsp;IMSYY</span>
<span class="set_version-text2">©&nbsp;Snavigation&nbsp;v&nbsp;1.2</span>
</div>
</div>
</div>
</div>
</div>
</div>
</div>
<!-- 版权信息 -->
<div class="foot">
<div class="power">Copyright&nbsp;&copy;&nbsp;2020
<script>
document.write(' - ' + (new Date()).getFullYear())
</script>&nbsp;<a href="https://imsyy.top">無名</a>&nbsp;&amp;&nbsp;
<!-- 以下信息请不要修改哦 -->
Made&nbsp;by&nbsp;<a href="https://github.com/imsyy/Snavigation" target="_blank">imsyy</a>
</div>
</div>
</section>
<!-- 主体内容结束 -->
<!-- noscript -->
<noscript>
<div class="noscript fixed-top">请开启 JavaScript</div>
</noscript>
<!-- JS -->
<script type="text/javascript" src="./js/main.js"></script>
<script type="text/javascript" src="./js/set.js"></script>
<script type="text/javascript" src="./js/js.cookie.js"></script>
</body>
</html> </html>

View File

@ -1,164 +0,0 @@
/*!
* JavaScript Cookie v2.2.1
* https://github.com/js-cookie/js-cookie
*
* Copyright 2006, 2015 Klaus Hartl & Fagner Brack
* Released under the MIT license
*/
;
(function (factory) {
var registeredInModuleLoader;
if (typeof define === 'function' && define.amd) {
define(factory);
registeredInModuleLoader = true;
}
if (typeof exports === 'object') {
module.exports = factory();
registeredInModuleLoader = true;
}
if (!registeredInModuleLoader) {
var OldCookies = window.Cookies;
var api = window.Cookies = factory();
api.noConflict = function () {
window.Cookies = OldCookies;
return api;
};
}
}(function () {
function extend() {
var i = 0;
var result = {};
for (; i < arguments.length; i++) {
var attributes = arguments[i];
for (var key in attributes) {
result[key] = attributes[key];
}
}
return result;
}
function decode(s) {
return s.replace(/(%[0-9A-Z]{2})+/g, decodeURIComponent);
}
function init(converter) {
function api() {}
function set(key, value, attributes) {
if (typeof document === 'undefined') {
return;
}
attributes = extend({
path: '/'
}, api.defaults, attributes);
if (typeof attributes.expires === 'number') {
attributes.expires = new Date(new Date() * 1 + attributes.expires * 864e+5);
}
// We're using "expires" because "max-age" is not supported by IE
attributes.expires = attributes.expires ? attributes.expires.toUTCString() : '';
try {
var result = JSON.stringify(value);
if (/^[\{\[]/.test(result)) {
value = result;
}
} catch (e) {}
value = converter.write ?
converter.write(value, key) :
encodeURIComponent(String(value))
.replace(/%(23|24|26|2B|3A|3C|3E|3D|2F|3F|40|5B|5D|5E|60|7B|7D|7C)/g, decodeURIComponent);
key = encodeURIComponent(String(key))
.replace(/%(23|24|26|2B|5E|60|7C)/g, decodeURIComponent)
.replace(/[\(\)]/g, escape);
var stringifiedAttributes = '';
for (var attributeName in attributes) {
if (!attributes[attributeName]) {
continue;
}
stringifiedAttributes += '; ' + attributeName;
if (attributes[attributeName] === true) {
continue;
}
// Considers RFC 6265 section 5.2:
// ...
// 3. If the remaining unparsed-attributes contains a %x3B (";")
// character:
// Consume the characters of the unparsed-attributes up to,
// not including, the first %x3B (";") character.
// ...
stringifiedAttributes += '=' + attributes[attributeName].split(';')[0];
}
return (document.cookie = key + '=' + value + stringifiedAttributes);
}
function get(key, json) {
if (typeof document === 'undefined') {
return;
}
var jar = {};
// To prevent the for loop in the first place assign an empty array
// in case there are no cookies at all.
var cookies = document.cookie ? document.cookie.split('; ') : [];
var i = 0;
for (; i < cookies.length; i++) {
var parts = cookies[i].split('=');
var cookie = parts.slice(1).join('=');
if (!json && cookie.charAt(0) === '"') {
cookie = cookie.slice(1, -1);
}
try {
var name = decode(parts[0]);
cookie = (converter.read || converter)(cookie, name) ||
decode(cookie);
if (json) {
try {
cookie = JSON.parse(cookie);
} catch (e) {}
}
jar[name] = cookie;
if (key === name) {
break;
}
} catch (e) {}
}
return key ? jar[key] : jar;
}
api.set = set;
api.get = function (key) {
return get(key, false /* read as raw */ );
};
api.getJSON = function (key) {
return get(key, true /* read as json */ );
};
api.remove = function (key, attributes) {
set(key, '', extend(attributes, {
expires: -1
}));
};
api.defaults = {};
api.withConverter = init;
return api;
}
return init(function () {});
}));

View File

@ -1,170 +0,0 @@
//加载完成后执行
window.addEventListener('load', function () {
//载入动画
$('#loading-box').attr('class', 'loaded');
$('#bg').css("cssText", "transform: scale(1);filter: blur(0px);transition: ease 1.5s;");
$('#section').css("cssText", "opacity: 1;transition: ease 1.5s;");
$('.cover').css("cssText", "opacity: 1;transition: ease 1.5s;");
//用户欢迎
iziToast.settings({
timeout: 3000,
backgroundColor: '#ffffff40',
titleColor: '#efefef',
messageColor: '#efefef',
progressBar: false,
close: false,
closeOnEscape: true,
position: 'topCenter',
transitionIn: 'bounceInDown',
transitionOut: 'flipOutX',
displayMode: 'replace',
layout: '1'
});
setTimeout(function () {
iziToast.show({
title: hello,
message: '欢迎来到 Snavigation'
});
}, 800);
//中文字体缓加载-此处写入字体源文件
//先行加载简体中文子集,后续补全字集
//由于压缩过后的中文字体仍旧过大,可转移至对象存储或 CDN 加载
const font = new FontFace(
"MiSans",
"url(" + "./font/MiSans-Regular.woff2" + ")"
);
document.fonts.add(font);
}, false)
//进入问候
now = new Date(), hour = now.getHours()
if (hour < 6) {
var hello = "凌晨好";
} else if (hour < 9) {
var hello = "早上好";
} else if (hour < 12) {
var hello = "上午好";
} else if (hour < 14) {
var hello = "中午好";
} else if (hour < 17) {
var hello = "下午好";
} else if (hour < 19) {
var hello = "傍晚好";
} else if (hour < 22) {
var hello = "晚上好";
} else {
var hello = "夜深了";
}
//获取时间
var t = null;
t = setTimeout(time, 1000);
function time() {
clearTimeout(t);
dt = new Date();
var mm = dt.getMonth() + 1;
var d = dt.getDate();
var weekday = ["周日", "周一", "周二", "周三", "周四", "周五", "周六"];
var day = dt.getDay();
var h = dt.getHours();
var m = dt.getMinutes();
if (h < 10) {
h = "0" + h;
}
if (m < 10) {
m = "0" + m;
}
$("#time_text").html(h + '<span id="point">:</span>' + m);
$("#day").html(mm + "&nbsp;月&nbsp;" + d + "&nbsp;日&nbsp;" + weekday[day]);
t = setTimeout(time, 1000);
}
//获取天气
//每日限量 100 次
//请前往 https://www.tianqiapi.com/index/doc?version=v6 申请(免费)
fetch('https://yiketianqi.com/api?unescape=1&version=v6&appid=43986679&appsecret=TksqGZT7')
.then(response => response.json())
.then(data => {
//$('#wea_text').html(data.wea + '&nbsp;' + data.tem_night + '℃' + '&nbsp;~&nbsp;' + data.tem_day + '℃')
$('#wea_text').text(data.wea)
$('#tem1').text(data.tem1)
$('#tem2').text(data.tem2)
})
.catch(console.error)
//Tab书签页
$(function () {
$(".mark .tab .tab-item").click(function () {
$(this).addClass("active").siblings().removeClass("active");
$(".products .mainCont").eq($(this).index()).css("display", "flex").siblings().css("display", "none");
})
})
//设置
$(function () {
$(".set .tabs .tab-items").click(function () {
$(this).addClass("actives").siblings().removeClass("actives");
$(".productss .mainConts").eq($(this).index()).css("display", "flex").siblings().css("display", "none");
})
})
//输入框为空时阻止跳转
$(window).keydown(function (e) {
var key = window.event ? e.keyCode : e.which;
if (key.toString() == "13") {
if ($(".wd").val() == "") {
return false;
}
}
});
//点击搜索按钮
$(".sou-button").click(function () {
if ($("body").attr("class") === "onsearch") {
if ($(".wd").val() != "") {
$("#search-submit").click();
}
}
});
//鼠标中键点击事件
$(window).mousedown(function (event) {
if (event.button == 1) {
$("#time_text").click();
}
});
//控制台输出
var styleTitle1 = `
font-size: 20px;
font-weight: 600;
color: rgb(244,167,89);
`
var styleTitle2 = `
font-size:12px;
color: rgb(244,167,89);
`
var styleContent = `
color: rgb(30,152,255);
`
var title1 = 'Snavigation'
var title2 = `
_____ __ __ _______ ____ __
|_ _| \\/ |/ ____\\ \\ / /\\ \\ / /
| | | \\ / | (___ \\ \\_/ / \\ \\_/ /
| | | |\\/| |\\___ \\ \\ / \\ /
_| |_| | | |____) | | | | |
|_____|_| |_|_____/ |_| |_|
`
var content = `
1.1
更新日期2022-07-12
Github: https://github.com/imsyy/Snavigation
`
console.log(`%c${title1} %c${title2}
%c${content}`, styleTitle1, styleTitle2, styleContent)

1216
js/set.js

File diff suppressed because it is too large Load Diff

24
package.json Normal file
View File

@ -0,0 +1,24 @@
{
"name": "snavigation",
"private": true,
"version": "0.0.0",
"type": "module",
"scripts": {
"dev": "vite",
"build": "vite build",
"preview": "vite preview"
},
"dependencies": {
"axios": "^1.4.0",
"axios-jsonp": "^1.0.4",
"pinia": "^2.1.4",
"pinia-plugin-persistedstate": "^3.2.0",
"sass": "^1.64.1",
"vue": "^3.3.4"
},
"devDependencies": {
"@vitejs/plugin-vue": "^4.2.3",
"terser": "^5.19.2",
"vite": "^4.4.5"
}
}

751
pnpm-lock.yaml Normal file
View File

@ -0,0 +1,751 @@
lockfileVersion: '6.0'
settings:
autoInstallPeers: true
excludeLinksFromLockfile: false
dependencies:
axios:
specifier: ^1.4.0
version: 1.4.0
axios-jsonp:
specifier: ^1.0.4
version: 1.0.4
pinia:
specifier: ^2.1.4
version: 2.1.4(vue@3.3.4)
pinia-plugin-persistedstate:
specifier: ^3.2.0
version: 3.2.0(pinia@2.1.4)
sass:
specifier: ^1.64.1
version: 1.64.1
vue:
specifier: ^3.3.4
version: 3.3.4
devDependencies:
'@vitejs/plugin-vue':
specifier: ^4.2.3
version: 4.2.3(vite@4.4.6)(vue@3.3.4)
terser:
specifier: ^5.19.2
version: 5.19.2
vite:
specifier: ^4.4.5
version: 4.4.6(sass@1.64.1)(terser@5.19.2)
packages:
/@babel/helper-string-parser@7.22.5:
resolution: {integrity: sha512-mM4COjgZox8U+JcXQwPijIZLElkgEpO5rsERVDJTc2qfCDfERyob6k5WegS14SX18IIjv+XD+GrqNumY5JRCDw==}
engines: {node: '>=6.9.0'}
/@babel/helper-validator-identifier@7.22.5:
resolution: {integrity: sha512-aJXu+6lErq8ltp+JhkJUfk1MTGyuA4v7f3pA+BJ5HLfNC6nAQ0Cpi9uOquUj8Hehg0aUiHzWQbOVJGao6ztBAQ==}
engines: {node: '>=6.9.0'}
/@babel/parser@7.22.7:
resolution: {integrity: sha512-7NF8pOkHP5o2vpmGgNGcfAeCvOYhGLyA3Z4eBQkT1RJlWu47n63bCs93QfJ2hIAFCil7L5P2IWhs1oToVgrL0Q==}
engines: {node: '>=6.0.0'}
hasBin: true
dependencies:
'@babel/types': 7.22.5
/@babel/types@7.22.5:
resolution: {integrity: sha512-zo3MIHGOkPOfoRXitsgHLjEXmlDaD/5KU1Uzuc9GNiZPhSqVxVRtxuPaSBZDsYZ9qV88AjtMtWW7ww98loJ9KA==}
engines: {node: '>=6.9.0'}
dependencies:
'@babel/helper-string-parser': 7.22.5
'@babel/helper-validator-identifier': 7.22.5
to-fast-properties: 2.0.0
/@esbuild/android-arm64@0.18.16:
resolution: {integrity: sha512-wsCqSPqLz+6Ov+OM4EthU43DyYVVyfn15S4j1bJzylDpc1r1jZFFfJQNfDuT8SlgwuqpmpJXK4uPlHGw6ve7eA==}
engines: {node: '>=12'}
cpu: [arm64]
os: [android]
requiresBuild: true
dev: true
optional: true
/@esbuild/android-arm@0.18.16:
resolution: {integrity: sha512-gCHjjQmA8L0soklKbLKA6pgsLk1byULuHe94lkZDzcO3/Ta+bbeewJioEn1Fr7kgy9NWNFy/C+MrBwC6I/WCug==}
engines: {node: '>=12'}
cpu: [arm]
os: [android]
requiresBuild: true
dev: true
optional: true
/@esbuild/android-x64@0.18.16:
resolution: {integrity: sha512-ldsTXolyA3eTQ1//4DS+E15xl0H/3DTRJaRL0/0PgkqDsI0fV/FlOtD+h0u/AUJr+eOTlZv4aC9gvfppo3C4sw==}
engines: {node: '>=12'}
cpu: [x64]
os: [android]
requiresBuild: true
dev: true
optional: true
/@esbuild/darwin-arm64@0.18.16:
resolution: {integrity: sha512-aBxruWCII+OtluORR/KvisEw0ALuw/qDQWvkoosA+c/ngC/Kwk0lLaZ+B++LLS481/VdydB2u6tYpWxUfnLAIw==}
engines: {node: '>=12'}
cpu: [arm64]
os: [darwin]
requiresBuild: true
dev: true
optional: true
/@esbuild/darwin-x64@0.18.16:
resolution: {integrity: sha512-6w4Dbue280+rp3LnkgmriS1icOUZDyPuZo/9VsuMUTns7SYEiOaJ7Ca1cbhu9KVObAWfmdjUl4gwy9TIgiO5eA==}
engines: {node: '>=12'}
cpu: [x64]
os: [darwin]
requiresBuild: true
dev: true
optional: true
/@esbuild/freebsd-arm64@0.18.16:
resolution: {integrity: sha512-x35fCebhe9s979DGKbVAwXUOcTmCIE32AIqB9CB1GralMIvxdnMLAw5CnID17ipEw9/3MvDsusj/cspYt2ZLNQ==}
engines: {node: '>=12'}
cpu: [arm64]
os: [freebsd]
requiresBuild: true
dev: true
optional: true
/@esbuild/freebsd-x64@0.18.16:
resolution: {integrity: sha512-YM98f+PeNXF3GbxIJlUsj+McUWG1irguBHkszCIwfr3BXtXZsXo0vqybjUDFfu9a8Wr7uUD/YSmHib+EeGAFlg==}
engines: {node: '>=12'}
cpu: [x64]
os: [freebsd]
requiresBuild: true
dev: true
optional: true
/@esbuild/linux-arm64@0.18.16:
resolution: {integrity: sha512-XIqhNUxJiuy+zsR77+H5Z2f7s4YRlriSJKtvx99nJuG5ATuJPjmZ9n0ANgnGlPCpXGSReFpgcJ7O3SMtzIFeiQ==}
engines: {node: '>=12'}
cpu: [arm64]
os: [linux]
requiresBuild: true
dev: true
optional: true
/@esbuild/linux-arm@0.18.16:
resolution: {integrity: sha512-b5ABb+5Ha2C9JkeZXV+b+OruR1tJ33ePmv9ZwMeETSEKlmu/WJ45XTTG+l6a2KDsQtJJ66qo/hbSGBtk0XVLHw==}
engines: {node: '>=12'}
cpu: [arm]
os: [linux]
requiresBuild: true
dev: true
optional: true
/@esbuild/linux-ia32@0.18.16:
resolution: {integrity: sha512-no+pfEpwnRvIyH+txbBAWtjxPU9grslmTBfsmDndj7bnBmr55rOo/PfQmRfz7Qg9isswt1FP5hBbWb23fRWnow==}
engines: {node: '>=12'}
cpu: [ia32]
os: [linux]
requiresBuild: true
dev: true
optional: true
/@esbuild/linux-loong64@0.18.16:
resolution: {integrity: sha512-Zbnczs9ZXjmo0oZSS0zbNlJbcwKXa/fcNhYQjahDs4Xg18UumpXG/lwM2lcSvHS3mTrRyCYZvJbmzYc4laRI1g==}
engines: {node: '>=12'}
cpu: [loong64]
os: [linux]
requiresBuild: true
dev: true
optional: true
/@esbuild/linux-mips64el@0.18.16:
resolution: {integrity: sha512-YMF7hih1HVR/hQVa/ot4UVffc5ZlrzEb3k2ip0nZr1w6fnYypll9td2qcoMLvd3o8j3y6EbJM3MyIcXIVzXvQQ==}
engines: {node: '>=12'}
cpu: [mips64el]
os: [linux]
requiresBuild: true
dev: true
optional: true
/@esbuild/linux-ppc64@0.18.16:
resolution: {integrity: sha512-Wkz++LZ29lDwUyTSEnzDaaP5OveOgTU69q9IyIw9WqLRxM4BjTBjz9un4G6TOvehWpf/J3gYVFN96TjGHrbcNQ==}
engines: {node: '>=12'}
cpu: [ppc64]
os: [linux]
requiresBuild: true
dev: true
optional: true
/@esbuild/linux-riscv64@0.18.16:
resolution: {integrity: sha512-LFMKZ30tk78/mUv1ygvIP+568bwf4oN6reG/uczXnz6SvFn4e2QUFpUpZY9iSJT6Qpgstrhef/nMykIXZtZWGQ==}
engines: {node: '>=12'}
cpu: [riscv64]
os: [linux]
requiresBuild: true
dev: true
optional: true
/@esbuild/linux-s390x@0.18.16:
resolution: {integrity: sha512-3ZC0BgyYHYKfZo3AV2/66TD/I9tlSBaW7eWTEIkrQQKfJIifKMMttXl9FrAg+UT0SGYsCRLI35Gwdmm96vlOjg==}
engines: {node: '>=12'}
cpu: [s390x]
os: [linux]
requiresBuild: true
dev: true
optional: true
/@esbuild/linux-x64@0.18.16:
resolution: {integrity: sha512-xu86B3647DihHJHv/wx3NCz2Dg1gjQ8bbf9cVYZzWKY+gsvxYmn/lnVlqDRazObc3UMwoHpUhNYaZset4X8IPA==}
engines: {node: '>=12'}
cpu: [x64]
os: [linux]
requiresBuild: true
dev: true
optional: true
/@esbuild/netbsd-x64@0.18.16:
resolution: {integrity: sha512-uVAgpimx9Ffw3xowtg/7qQPwHFx94yCje+DoBx+LNm2ePDpQXHrzE+Sb0Si2VBObYz+LcRps15cq+95YM7gkUw==}
engines: {node: '>=12'}
cpu: [x64]
os: [netbsd]
requiresBuild: true
dev: true
optional: true
/@esbuild/openbsd-x64@0.18.16:
resolution: {integrity: sha512-6OjCQM9wf7z8/MBi6BOWaTL2AS/SZudsZtBziXMtNI8r/U41AxS9x7jn0ATOwVy08OotwkPqGRMkpPR2wcTJXA==}
engines: {node: '>=12'}
cpu: [x64]
os: [openbsd]
requiresBuild: true
dev: true
optional: true
/@esbuild/sunos-x64@0.18.16:
resolution: {integrity: sha512-ZoNkruFYJp9d1LbUYCh8awgQDvB9uOMZqlQ+gGEZR7v6C+N6u7vPr86c+Chih8niBR81Q/bHOSKGBK3brJyvkQ==}
engines: {node: '>=12'}
cpu: [x64]
os: [sunos]
requiresBuild: true
dev: true
optional: true
/@esbuild/win32-arm64@0.18.16:
resolution: {integrity: sha512-+j4anzQ9hrs+iqO+/wa8UE6TVkKua1pXUb0XWFOx0FiAj6R9INJ+WE//1/Xo6FG1vB5EpH3ko+XcgwiDXTxcdw==}
engines: {node: '>=12'}
cpu: [arm64]
os: [win32]
requiresBuild: true
dev: true
optional: true
/@esbuild/win32-ia32@0.18.16:
resolution: {integrity: sha512-5PFPmq3sSKTp9cT9dzvI67WNfRZGvEVctcZa1KGjDDu4n3H8k59Inbk0du1fz0KrAbKKNpJbdFXQMDUz7BG4rQ==}
engines: {node: '>=12'}
cpu: [ia32]
os: [win32]
requiresBuild: true
dev: true
optional: true
/@esbuild/win32-x64@0.18.16:
resolution: {integrity: sha512-sCIVrrtcWN5Ua7jYXNG1xD199IalrbfV2+0k/2Zf2OyV2FtnQnMgdzgpRAbi4AWlKJj1jkX+M+fEGPQj6BQB4w==}
engines: {node: '>=12'}
cpu: [x64]
os: [win32]
requiresBuild: true
dev: true
optional: true
/@jridgewell/gen-mapping@0.3.3:
resolution: {integrity: sha512-HLhSWOLRi875zjjMG/r+Nv0oCW8umGb0BgEhyX3dDX3egwZtB8PqLnjz3yedt8R5StBrzcg4aBpnh8UA9D1BoQ==}
engines: {node: '>=6.0.0'}
dependencies:
'@jridgewell/set-array': 1.1.2
'@jridgewell/sourcemap-codec': 1.4.15
'@jridgewell/trace-mapping': 0.3.18
dev: true
/@jridgewell/resolve-uri@3.1.0:
resolution: {integrity: sha512-F2msla3tad+Mfht5cJq7LSXcdudKTWCVYUgw6pLFOOHSTtZlj6SWNYAp+AhuqLmWdBO2X5hPrLcu8cVP8fy28w==}
engines: {node: '>=6.0.0'}
dev: true
/@jridgewell/set-array@1.1.2:
resolution: {integrity: sha512-xnkseuNADM0gt2bs+BvhO0p78Mk762YnZdsuzFV018NoG1Sj1SCQvpSqa7XUaTam5vAGasABV9qXASMKnFMwMw==}
engines: {node: '>=6.0.0'}
dev: true
/@jridgewell/source-map@0.3.5:
resolution: {integrity: sha512-UTYAUj/wviwdsMfzoSJspJxbkH5o1snzwX0//0ENX1u/55kkZZkcTZP6u9bwKGkv+dkk9at4m1Cpt0uY80kcpQ==}
dependencies:
'@jridgewell/gen-mapping': 0.3.3
'@jridgewell/trace-mapping': 0.3.18
dev: true
/@jridgewell/sourcemap-codec@1.4.14:
resolution: {integrity: sha512-XPSJHWmi394fuUuzDnGz1wiKqWfo1yXecHQMRf2l6hztTO+nPru658AyDngaBe7isIxEkRsPR3FZh+s7iVa4Uw==}
dev: true
/@jridgewell/sourcemap-codec@1.4.15:
resolution: {integrity: sha512-eF2rxCRulEKXHTRiDrDy6erMYWqNw4LPdQ8UQA4huuxaQsVeRPFl2oM8oDGxMFhJUWZf9McpLtJasDDZb/Bpeg==}
/@jridgewell/trace-mapping@0.3.18:
resolution: {integrity: sha512-w+niJYzMHdd7USdiH2U6869nqhD2nbfZXND5Yp93qIbEmnDNk7PD48o+YchRVpzMU7M6jVCbenTR7PA1FLQ9pA==}
dependencies:
'@jridgewell/resolve-uri': 3.1.0
'@jridgewell/sourcemap-codec': 1.4.14
dev: true
/@vitejs/plugin-vue@4.2.3(vite@4.4.6)(vue@3.3.4):
resolution: {integrity: sha512-R6JDUfiZbJA9cMiguQ7jxALsgiprjBeHL5ikpXfJCH62pPHtI+JdJ5xWj6Ev73yXSlYl86+blXn1kZHQ7uElxw==}
engines: {node: ^14.18.0 || >=16.0.0}
peerDependencies:
vite: ^4.0.0
vue: ^3.2.25
dependencies:
vite: 4.4.6(sass@1.64.1)(terser@5.19.2)
vue: 3.3.4
dev: true
/@vue/compiler-core@3.3.4:
resolution: {integrity: sha512-cquyDNvZ6jTbf/+x+AgM2Arrp6G4Dzbb0R64jiG804HRMfRiFXWI6kqUVqZ6ZR0bQhIoQjB4+2bhNtVwndW15g==}
dependencies:
'@babel/parser': 7.22.7
'@vue/shared': 3.3.4
estree-walker: 2.0.2
source-map-js: 1.0.2
/@vue/compiler-dom@3.3.4:
resolution: {integrity: sha512-wyM+OjOVpuUukIq6p5+nwHYtj9cFroz9cwkfmP9O1nzH68BenTTv0u7/ndggT8cIQlnBeOo6sUT/gvHcIkLA5w==}
dependencies:
'@vue/compiler-core': 3.3.4
'@vue/shared': 3.3.4
/@vue/compiler-sfc@3.3.4:
resolution: {integrity: sha512-6y/d8uw+5TkCuzBkgLS0v3lSM3hJDntFEiUORM11pQ/hKvkhSKZrXW6i69UyXlJQisJxuUEJKAWEqWbWsLeNKQ==}
dependencies:
'@babel/parser': 7.22.7
'@vue/compiler-core': 3.3.4
'@vue/compiler-dom': 3.3.4
'@vue/compiler-ssr': 3.3.4
'@vue/reactivity-transform': 3.3.4
'@vue/shared': 3.3.4
estree-walker: 2.0.2
magic-string: 0.30.1
postcss: 8.4.27
source-map-js: 1.0.2
/@vue/compiler-ssr@3.3.4:
resolution: {integrity: sha512-m0v6oKpup2nMSehwA6Uuu+j+wEwcy7QmwMkVNVfrV9P2qE5KshC6RwOCq8fjGS/Eak/uNb8AaWekfiXxbBB6gQ==}
dependencies:
'@vue/compiler-dom': 3.3.4
'@vue/shared': 3.3.4
/@vue/devtools-api@6.5.0:
resolution: {integrity: sha512-o9KfBeaBmCKl10usN4crU53fYtC1r7jJwdGKjPT24t348rHxgfpZ0xL3Xm/gLUYnc0oTp8LAmrxOeLyu6tbk2Q==}
dev: false
/@vue/reactivity-transform@3.3.4:
resolution: {integrity: sha512-MXgwjako4nu5WFLAjpBnCj/ieqcjE2aJBINUNQzkZQfzIZA4xn+0fV1tIYBJvvva3N3OvKGofRLvQIwEQPpaXw==}
dependencies:
'@babel/parser': 7.22.7
'@vue/compiler-core': 3.3.4
'@vue/shared': 3.3.4
estree-walker: 2.0.2
magic-string: 0.30.1
/@vue/reactivity@3.3.4:
resolution: {integrity: sha512-kLTDLwd0B1jG08NBF3R5rqULtv/f8x3rOFByTDz4J53ttIQEDmALqKqXY0J+XQeN0aV2FBxY8nJDf88yvOPAqQ==}
dependencies:
'@vue/shared': 3.3.4
/@vue/runtime-core@3.3.4:
resolution: {integrity: sha512-R+bqxMN6pWO7zGI4OMlmvePOdP2c93GsHFM/siJI7O2nxFRzj55pLwkpCedEY+bTMgp5miZ8CxfIZo3S+gFqvA==}
dependencies:
'@vue/reactivity': 3.3.4
'@vue/shared': 3.3.4
/@vue/runtime-dom@3.3.4:
resolution: {integrity: sha512-Aj5bTJ3u5sFsUckRghsNjVTtxZQ1OyMWCr5dZRAPijF/0Vy4xEoRCwLyHXcj4D0UFbJ4lbx3gPTgg06K/GnPnQ==}
dependencies:
'@vue/runtime-core': 3.3.4
'@vue/shared': 3.3.4
csstype: 3.1.2
/@vue/server-renderer@3.3.4(vue@3.3.4):
resolution: {integrity: sha512-Q6jDDzR23ViIb67v+vM1Dqntu+HUexQcsWKhhQa4ARVzxOY2HbC7QRW/ggkDBd5BU+uM1sV6XOAP0b216o34JQ==}
peerDependencies:
vue: 3.3.4
dependencies:
'@vue/compiler-ssr': 3.3.4
'@vue/shared': 3.3.4
vue: 3.3.4
/@vue/shared@3.3.4:
resolution: {integrity: sha512-7OjdcV8vQ74eiz1TZLzZP4JwqM5fA94K6yntPS5Z25r9HDuGNzaGdgvwKYq6S+MxwF0TFRwe50fIR/MYnakdkQ==}
/acorn@8.10.0:
resolution: {integrity: sha512-F0SAmZ8iUtS//m8DmCTA0jlh6TDKkHQyK6xc6V4KDTyZKA9dnvX9/3sRTVQrWm79glUAZbnmmNcdYwUIHWVybw==}
engines: {node: '>=0.4.0'}
hasBin: true
dev: true
/anymatch@3.1.3:
resolution: {integrity: sha512-KMReFUr0B4t+D+OBkjR3KYqvocp2XaSzO55UcB6mgQMd3KbcE+mWTyvVV7D/zsdEbNnV6acZUutkiHQXvTr1Rw==}
engines: {node: '>= 8'}
dependencies:
normalize-path: 3.0.0
picomatch: 2.3.1
/asynckit@0.4.0:
resolution: {integrity: sha512-Oei9OH4tRh0YqU3GxhX79dM/mwVgvbZJaSNaRk+bshkj0S5cfHcgYakreBjrHwatXKbz+IoIdYLxrKim2MjW0Q==}
dev: false
/axios-jsonp@1.0.4:
resolution: {integrity: sha512-KI5Fc4ery6DR+oneXG09hPZfGuNUW8Lblhe750h53Z0Eh5MRsrHn49YitDU4RsMk0HV+12zcvL2Q51QkOLGdIQ==}
dev: false
/axios@1.4.0:
resolution: {integrity: sha512-S4XCWMEmzvo64T9GfvQDOXgYRDJ/wsSZc7Jvdgx5u1sd0JwsuPLqb3SYmusag+edF6ziyMensPVqLTSc1PiSEA==}
dependencies:
follow-redirects: 1.15.2
form-data: 4.0.0
proxy-from-env: 1.1.0
transitivePeerDependencies:
- debug
dev: false
/binary-extensions@2.2.0:
resolution: {integrity: sha512-jDctJ/IVQbZoJykoeHbhXpOlNBqGNcwXJKJog42E5HDPUwQTSdjCHdihjj0DlnheQ7blbT6dHOafNAiS8ooQKA==}
engines: {node: '>=8'}
/braces@3.0.2:
resolution: {integrity: sha512-b8um+L1RzM3WDSzvhm6gIz1yfTbBt6YTlcEKAvsmqCZZFw46z626lVj9j1yEPW33H5H+lBQpZMP1k8l+78Ha0A==}
engines: {node: '>=8'}
dependencies:
fill-range: 7.0.1
/buffer-from@1.1.2:
resolution: {integrity: sha512-E+XQCRwSbaaiChtv6k6Dwgc+bx+Bs6vuKJHHl5kox/BaKbhiXzqQOwK4cO22yElGp2OCmjwVhT3HmxgyPGnJfQ==}
dev: true
/chokidar@3.5.3:
resolution: {integrity: sha512-Dr3sfKRP6oTcjf2JmUmFJfeVMvXBdegxB0iVQ5eb2V10uFJUCAS8OByZdVAyVb8xXNz3GjjTgj9kLWsZTqE6kw==}
engines: {node: '>= 8.10.0'}
dependencies:
anymatch: 3.1.3
braces: 3.0.2
glob-parent: 5.1.2
is-binary-path: 2.1.0
is-glob: 4.0.3
normalize-path: 3.0.0
readdirp: 3.6.0
optionalDependencies:
fsevents: 2.3.2
/combined-stream@1.0.8:
resolution: {integrity: sha512-FQN4MRfuJeHf7cBbBMJFXhKSDq+2kAArBlmRBvcvFE5BB1HZKXtSFASDhdlz9zOYwxh8lDdnvmMOe/+5cdoEdg==}
engines: {node: '>= 0.8'}
dependencies:
delayed-stream: 1.0.0
dev: false
/commander@2.20.3:
resolution: {integrity: sha512-GpVkmM8vF2vQUkj2LvZmD35JxeJOLCwJ9cUkugyk2nuhbv3+mJvpLYYt+0+USMxE+oj+ey/lJEnhZw75x/OMcQ==}
dev: true
/csstype@3.1.2:
resolution: {integrity: sha512-I7K1Uu0MBPzaFKg4nI5Q7Vs2t+3gWWW648spaF+Rg7pI9ds18Ugn+lvg4SHczUdKlHI5LWBXyqfS8+DufyBsgQ==}
/delayed-stream@1.0.0:
resolution: {integrity: sha512-ZySD7Nf91aLB0RxL4KGrKHBXl7Eds1DAmEdcoVawXnLD7SDhpNgtuII2aAkg7a7QS41jxPSZ17p4VdGnMHk3MQ==}
engines: {node: '>=0.4.0'}
dev: false
/esbuild@0.18.16:
resolution: {integrity: sha512-1xLsOXrDqwdHxyXb/x/SOyg59jpf/SH7YMvU5RNSU7z3TInaASNJWNFJ6iRvLvLETZMasF3d1DdZLg7sgRimRQ==}
engines: {node: '>=12'}
hasBin: true
requiresBuild: true
optionalDependencies:
'@esbuild/android-arm': 0.18.16
'@esbuild/android-arm64': 0.18.16
'@esbuild/android-x64': 0.18.16
'@esbuild/darwin-arm64': 0.18.16
'@esbuild/darwin-x64': 0.18.16
'@esbuild/freebsd-arm64': 0.18.16
'@esbuild/freebsd-x64': 0.18.16
'@esbuild/linux-arm': 0.18.16
'@esbuild/linux-arm64': 0.18.16
'@esbuild/linux-ia32': 0.18.16
'@esbuild/linux-loong64': 0.18.16
'@esbuild/linux-mips64el': 0.18.16
'@esbuild/linux-ppc64': 0.18.16
'@esbuild/linux-riscv64': 0.18.16
'@esbuild/linux-s390x': 0.18.16
'@esbuild/linux-x64': 0.18.16
'@esbuild/netbsd-x64': 0.18.16
'@esbuild/openbsd-x64': 0.18.16
'@esbuild/sunos-x64': 0.18.16
'@esbuild/win32-arm64': 0.18.16
'@esbuild/win32-ia32': 0.18.16
'@esbuild/win32-x64': 0.18.16
dev: true
/estree-walker@2.0.2:
resolution: {integrity: sha512-Rfkk/Mp/DL7JVje3u18FxFujQlTNR2q6QfMSMB7AvCBx91NGj/ba3kCfza0f6dVDbw7YlRf/nDrn7pQrCCyQ/w==}
/fill-range@7.0.1:
resolution: {integrity: sha512-qOo9F+dMUmC2Lcb4BbVvnKJxTPjCm+RRpe4gDuGrzkL7mEVl/djYSu2OdQ2Pa302N4oqkSg9ir6jaLWJ2USVpQ==}
engines: {node: '>=8'}
dependencies:
to-regex-range: 5.0.1
/follow-redirects@1.15.2:
resolution: {integrity: sha512-VQLG33o04KaQ8uYi2tVNbdrWp1QWxNNea+nmIB4EVM28v0hmP17z7aG1+wAkNzVq4KeXTq3221ye5qTJP91JwA==}
engines: {node: '>=4.0'}
peerDependencies:
debug: '*'
peerDependenciesMeta:
debug:
optional: true
dev: false
/form-data@4.0.0:
resolution: {integrity: sha512-ETEklSGi5t0QMZuiXoA/Q6vcnxcLQP5vdugSpuAyi6SVGi2clPPp+xgEhuMaHC+zGgn31Kd235W35f7Hykkaww==}
engines: {node: '>= 6'}
dependencies:
asynckit: 0.4.0
combined-stream: 1.0.8
mime-types: 2.1.35
dev: false
/fsevents@2.3.2:
resolution: {integrity: sha512-xiqMQR4xAeHTuB9uWm+fFRcIOgKBMiOBP+eXiyT7jsgVCq1bkVygt00oASowB7EdtpOHaaPgKt812P9ab+DDKA==}
engines: {node: ^8.16.0 || ^10.6.0 || >=11.0.0}
os: [darwin]
requiresBuild: true
optional: true
/glob-parent@5.1.2:
resolution: {integrity: sha512-AOIgSQCepiJYwP3ARnGx+5VnTu2HBYdzbGP45eLw1vr3zB3vZLeyed1sC9hnbcOc9/SrMyM5RPQrkGz4aS9Zow==}
engines: {node: '>= 6'}
dependencies:
is-glob: 4.0.3
/immutable@4.3.1:
resolution: {integrity: sha512-lj9cnmB/kVS0QHsJnYKD1uo3o39nrbKxszjnqS9Fr6NB7bZzW45U6WSGBPKXDL/CvDKqDNPA4r3DoDQ8GTxo2A==}
/is-binary-path@2.1.0:
resolution: {integrity: sha512-ZMERYes6pDydyuGidse7OsHxtbI7WVeUEozgR/g7rd0xUimYNlvZRE/K2MgZTjWy725IfelLeVcEM97mmtRGXw==}
engines: {node: '>=8'}
dependencies:
binary-extensions: 2.2.0
/is-extglob@2.1.1:
resolution: {integrity: sha512-SbKbANkN603Vi4jEZv49LeVJMn4yGwsbzZworEoyEiutsN3nJYdbO36zfhGJ6QEDpOZIFkDtnq5JRxmvl3jsoQ==}
engines: {node: '>=0.10.0'}
/is-glob@4.0.3:
resolution: {integrity: sha512-xelSayHH36ZgE7ZWhli7pW34hNbNl8Ojv5KVmkJD4hBdD3th8Tfk9vYasLM+mXWOZhFkgZfxhLSnrwRr4elSSg==}
engines: {node: '>=0.10.0'}
dependencies:
is-extglob: 2.1.1
/is-number@7.0.0:
resolution: {integrity: sha512-41Cifkg6e8TylSpdtTpeLVMqvSBEVzTttHvERD741+pnZ8ANv0004MRL43QKPDlK9cGvNp6NZWZUBlbGXYxxng==}
engines: {node: '>=0.12.0'}
/magic-string@0.30.1:
resolution: {integrity: sha512-mbVKXPmS0z0G4XqFDCTllmDQ6coZzn94aMlb0o/A4HEHJCKcanlDZwYJgwnkmgD3jyWhUgj9VsPrfd972yPffA==}
engines: {node: '>=12'}
dependencies:
'@jridgewell/sourcemap-codec': 1.4.15
/mime-db@1.52.0:
resolution: {integrity: sha512-sPU4uV7dYlvtWJxwwxHD0PuihVNiE7TyAbQ5SWxDCB9mUYvOgroQOwYQQOKPJ8CIbE+1ETVlOoK1UC2nU3gYvg==}
engines: {node: '>= 0.6'}
dev: false
/mime-types@2.1.35:
resolution: {integrity: sha512-ZDY+bPm5zTTF+YpCrAU9nK0UgICYPT0QtT1NZWFv4s++TNkcgVaT0g6+4R2uI4MjQjzysHB1zxuWL50hzaeXiw==}
engines: {node: '>= 0.6'}
dependencies:
mime-db: 1.52.0
dev: false
/nanoid@3.3.6:
resolution: {integrity: sha512-BGcqMMJuToF7i1rt+2PWSNVnWIkGCU78jBG3RxO/bZlnZPK2Cmi2QaffxGO/2RvWi9sL+FAiRiXMgsyxQ1DIDA==}
engines: {node: ^10 || ^12 || ^13.7 || ^14 || >=15.0.1}
hasBin: true
/normalize-path@3.0.0:
resolution: {integrity: sha512-6eZs5Ls3WtCisHWp9S2GUy8dqkpGi4BVSz3GaqiE6ezub0512ESztXUwUB6C6IKbQkY2Pnb/mD4WYojCRwcwLA==}
engines: {node: '>=0.10.0'}
/picocolors@1.0.0:
resolution: {integrity: sha512-1fygroTLlHu66zi26VoTDv8yRgm0Fccecssto+MhsZ0D/DGW2sm8E8AjW7NU5VVTRt5GxbeZ5qBuJr+HyLYkjQ==}
/picomatch@2.3.1:
resolution: {integrity: sha512-JU3teHTNjmE2VCGFzuY8EXzCDVwEqB2a8fsIvwaStHhAWJEeVd1o1QD80CU6+ZdEXXSLbSsuLwJjkCBWqRQUVA==}
engines: {node: '>=8.6'}
/pinia-plugin-persistedstate@3.2.0(pinia@2.1.4):
resolution: {integrity: sha512-tZbNGf2vjAQcIm7alK40sE51Qu/m9oWr+rEgNm/2AWr1huFxj72CjvpQcIQzMknDBJEkQznCLAGtJTIcLKrKdw==}
peerDependencies:
pinia: ^2.0.0
dependencies:
pinia: 2.1.4(vue@3.3.4)
dev: false
/pinia@2.1.4(vue@3.3.4):
resolution: {integrity: sha512-vYlnDu+Y/FXxv1ABo1vhjC+IbqvzUdiUC3sfDRrRyY2CQSrqqaa+iiHmqtARFxJVqWQMCJfXx1PBvFs9aJVLXQ==}
peerDependencies:
'@vue/composition-api': ^1.4.0
typescript: '>=4.4.4'
vue: ^2.6.14 || ^3.3.0
peerDependenciesMeta:
'@vue/composition-api':
optional: true
typescript:
optional: true
dependencies:
'@vue/devtools-api': 6.5.0
vue: 3.3.4
vue-demi: 0.14.5(vue@3.3.4)
dev: false
/postcss@8.4.27:
resolution: {integrity: sha512-gY/ACJtJPSmUFPDCHtX78+01fHa64FaU4zaaWfuh1MhGJISufJAH4cun6k/8fwsHYeK4UQmENQK+tRLCFJE8JQ==}
engines: {node: ^10 || ^12 || >=14}
dependencies:
nanoid: 3.3.6
picocolors: 1.0.0
source-map-js: 1.0.2
/proxy-from-env@1.1.0:
resolution: {integrity: sha512-D+zkORCbA9f1tdWRK0RaCR3GPv50cMxcrz4X8k5LTSUD1Dkw47mKJEZQNunItRTkWwgtaUSo1RVFRIG9ZXiFYg==}
dev: false
/readdirp@3.6.0:
resolution: {integrity: sha512-hOS089on8RduqdbhvQ5Z37A0ESjsqz6qnRcffsMU3495FuTdqSm+7bhJ29JvIOsBDEEnan5DPu9t3To9VRlMzA==}
engines: {node: '>=8.10.0'}
dependencies:
picomatch: 2.3.1
/rollup@3.26.3:
resolution: {integrity: sha512-7Tin0C8l86TkpcMtXvQu6saWH93nhG3dGQ1/+l5V2TDMceTxO7kDiK6GzbfLWNNxqJXm591PcEZUozZm51ogwQ==}
engines: {node: '>=14.18.0', npm: '>=8.0.0'}
hasBin: true
optionalDependencies:
fsevents: 2.3.2
dev: true
/sass@1.64.1:
resolution: {integrity: sha512-16rRACSOFEE8VN7SCgBu1MpYCyN7urj9At898tyzdXFhC+a+yOX5dXwAR7L8/IdPJ1NB8OYoXmD55DM30B2kEQ==}
engines: {node: '>=14.0.0'}
hasBin: true
dependencies:
chokidar: 3.5.3
immutable: 4.3.1
source-map-js: 1.0.2
/source-map-js@1.0.2:
resolution: {integrity: sha512-R0XvVJ9WusLiqTCEiGCmICCMplcCkIwwR11mOSD9CR5u+IXYdiseeEuXCVAjS54zqwkLcPNnmU4OeJ6tUrWhDw==}
engines: {node: '>=0.10.0'}
/source-map-support@0.5.21:
resolution: {integrity: sha512-uBHU3L3czsIyYXKX88fdrGovxdSCoTGDRZ6SYXtSRxLZUzHg5P/66Ht6uoUlHu9EZod+inXhKo3qQgwXUT/y1w==}
dependencies:
buffer-from: 1.1.2
source-map: 0.6.1
dev: true
/source-map@0.6.1:
resolution: {integrity: sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g==}
engines: {node: '>=0.10.0'}
dev: true
/terser@5.19.2:
resolution: {integrity: sha512-qC5+dmecKJA4cpYxRa5aVkKehYsQKc+AHeKl0Oe62aYjBL8ZA33tTljktDHJSaxxMnbI5ZYw+o/S2DxxLu8OfA==}
engines: {node: '>=10'}
hasBin: true
dependencies:
'@jridgewell/source-map': 0.3.5
acorn: 8.10.0
commander: 2.20.3
source-map-support: 0.5.21
dev: true
/to-fast-properties@2.0.0:
resolution: {integrity: sha512-/OaKK0xYrs3DmxRYqL/yDc+FxFUVYhDlXMhRmv3z915w2HF1tnN1omB354j8VUGO/hbRzyD6Y3sA7v7GS/ceog==}
engines: {node: '>=4'}
/to-regex-range@5.0.1:
resolution: {integrity: sha512-65P7iz6X5yEr1cwcgvQxbbIw7Uk3gOy5dIdtZ4rDveLqhrdJP+Li/Hx6tyK0NEb+2GCyneCMJiGqrADCSNk8sQ==}
engines: {node: '>=8.0'}
dependencies:
is-number: 7.0.0
/vite@4.4.6(sass@1.64.1)(terser@5.19.2):
resolution: {integrity: sha512-EY6Mm8vJ++S3D4tNAckaZfw3JwG3wa794Vt70M6cNJ6NxT87yhq7EC8Rcap3ahyHdo8AhCmV9PTk+vG1HiYn1A==}
engines: {node: ^14.18.0 || >=16.0.0}
hasBin: true
peerDependencies:
'@types/node': '>= 14'
less: '*'
lightningcss: ^1.21.0
sass: '*'
stylus: '*'
sugarss: '*'
terser: ^5.4.0
peerDependenciesMeta:
'@types/node':
optional: true
less:
optional: true
lightningcss:
optional: true
sass:
optional: true
stylus:
optional: true
sugarss:
optional: true
terser:
optional: true
dependencies:
esbuild: 0.18.16
postcss: 8.4.27
rollup: 3.26.3
sass: 1.64.1
terser: 5.19.2
optionalDependencies:
fsevents: 2.3.2
dev: true
/vue-demi@0.14.5(vue@3.3.4):
resolution: {integrity: sha512-o9NUVpl/YlsGJ7t+xuqJKx8EBGf1quRhCiT6D/J0pfwmk9zUwYkC7yrF4SZCe6fETvSM3UNL2edcbYrSyc4QHA==}
engines: {node: '>=12'}
hasBin: true
requiresBuild: true
peerDependencies:
'@vue/composition-api': ^1.0.0-rc.1
vue: ^3.0.0-0 || ^2.6.0
peerDependenciesMeta:
'@vue/composition-api':
optional: true
dependencies:
vue: 3.3.4
dev: false
/vue@3.3.4:
resolution: {integrity: sha512-VTyEYn3yvIeY1Py0WaYGZsXnz3y5UnGi62GjVEqvEGPl6nxbOrCXbVOTQWBEJUqAyTUk2uJ5JLVnYJ6ZzGbrSw==}
dependencies:
'@vue/compiler-dom': 3.3.4
'@vue/compiler-sfc': 3.3.4
'@vue/runtime-dom': 3.3.4
'@vue/server-renderer': 3.3.4(vue@3.3.4)
'@vue/shared': 3.3.4

BIN
public/background/bg1.jpg Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 78 KiB

BIN
public/background/bg2.jpg Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 206 KiB

BIN
public/background/bg3.jpg Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 254 KiB

View File

Before

Width:  |  Height:  |  Size: 1.9 KiB

After

Width:  |  Height:  |  Size: 1.9 KiB

View File

Before

Width:  |  Height:  |  Size: 4.3 KiB

After

Width:  |  Height:  |  Size: 4.3 KiB

56
src/App.vue Normal file
View File

@ -0,0 +1,56 @@
<template>
<Cover />
<Transition name="fade" mode="out-in">
<main v-if="status.imgLoadStatus" id="main" @click="mainClick">
<WeatherTime />
<SearchInp />
<Footer />
</main>
<div v-else id="loading">
<img src="/icon/logo.png" alt="logo" class="logo" />
<span class="tip">开发中</span>
</div>
</Transition>
</template>
<script setup>
import { statusStore } from "@/stores";
import Cover from "@/components/Cover.vue";
import WeatherTime from "@/components/WeatherTime.vue";
import SearchInp from "@/components/SearchInp.vue";
import Footer from "@/components/Footer.vue";
const status = statusStore();
//
const mainClick = () => {
status.setSiteStatus("normal");
};
</script>
<style lang="scss" scoped>
#main,
#loading {
position: absolute;
top: 0;
left: 0;
width: 100%;
height: 100%;
display: flex;
flex-direction: column;
justify-content: center;
align-items: center;
}
#loading {
color: var(--main-text-color);
.logo {
width: 100px;
height: 100px;
margin-bottom: 24px;
animation: logo-breathe 3s infinite alternate;
}
.tip {
font-size: 20px;
}
}
</style>

32
src/api/index.js Normal file
View File

@ -0,0 +1,32 @@
import axios from "@/utils/request";
import jsonpAdapter from "axios-jsonp";
/**
* 获取天气
* https://api.oioweb.cn/doc/weather/GetWeather
*/
export const getWeather = () => {
return axios({
method: "GET",
url: "https://api.oioweb.cn/api/weather/GetWeather",
});
};
/**
* 获取搜索建议
* https://suggestion.baidu.com
* @param {String} keyWord - 搜索关键字
*/
export const getSearchSuggestions = async (keyWord) => {
try {
const response = await axios({
url: `https://suggestion.baidu.com/su?wd=${keyWord}&cb=json`,
adapter: jsonpAdapter,
callbackParamName: "cb",
});
return response.s;
} catch (error) {
console.error("处理搜索建议发生错误:", error);
return null;
}
};

111
src/components/Cover.vue Normal file
View File

@ -0,0 +1,111 @@
<template>
<div :class="status.siteStatus !== 'normal' ? 'cover focus' : 'cover'">
<img
v-show="status.imgLoadStatus"
class="background"
alt="background"
:src="bgUrl"
@load="imgLoadComplete"
@error.once="imgLoadError"
/>
<Transition name="fade">
<div v-if="set.showBackgroundGray" class="gray" />
</Transition>
</div>
</template>
<script setup>
import { ref, onMounted, onBeforeUnmount } from "vue";
import { statusStore, setStore } from "@/stores";
const set = setStore();
const status = statusStore();
const bgUrl = ref(null);
const imgTimeout = ref(null);
//
// Math.random()
const bgRandom = Math.floor(Math.random() * 3 + 1);
//
const setBgUrl = () => {
const { backgroundType } = set;
switch (backgroundType) {
case 0:
bgUrl.value = `/background/bg${bgRandom}.jpg`;
break;
case 1:
const isMobile = window.innerWidth < 768;
bgUrl.value = `https://api.dujin.org/bing/${isMobile ? "m" : "1920"}.php`;
break;
case 2:
bgUrl.value = "https://api.aixiaowai.cn/gqapi/gqapi.php";
break;
case 3:
bgUrl.value = "https://api.aixiaowai.cn/api/api.php";
break;
default:
break;
}
};
//
const imgLoadComplete = () => {
imgTimeout.value = setTimeout(() => {
status.setImgLoadStatus(true);
console.log("壁纸加载完成");
}, 500);
};
//
const imgLoadError = () => {
console.error("图片加载失败:", bgUrl.value);
bgUrl.value = `/background/bg${bgRandom}.jpg`;
};
onMounted(() => {
setBgUrl();
});
onBeforeUnmount(() => {
clearTimeout(imgTimeout.value);
});
</script>
<style lang="scss" scoped>
.cover {
width: 100%;
height: 100%;
position: relative;
background-color: var(--body-background-color);
&.focus {
.background {
filter: blur(10px) brightness(0.8);
transform: scale(1.1);
}
}
.background {
position: absolute;
left: 0;
top: 0;
width: 100%;
height: 100%;
object-fit: cover;
backface-visibility: hidden;
transition: filter 0.3s, transform 0.3s;
animation: fade-blur-in 1s cubic-bezier(0.25, 0.46, 0.45, 0.94);
}
.gray {
position: absolute;
left: 0;
top: 0;
width: 100%;
height: 100%;
background-image: radial-gradient(
rgba(0, 0, 0, 0) 0,
rgba(0, 0, 0, 0.5) 100%
),
radial-gradient(rgba(0, 0, 0, 0) 33%, rgba(0, 0, 0, 0.3) 166%);
}
}
</style>

17
src/components/Footer.vue Normal file
View File

@ -0,0 +1,17 @@
<template>
<footer id="footer">114514</footer>
</template>
<style lang="scss" scoped>
#footer {
position: absolute;
display: flex;
align-items: center;
justify-content: center;
bottom: 0;
height: 60px;
width: 100%;
font-size: 14px;
color: var(--main-text-color);
}
</style>

View File

@ -0,0 +1,189 @@
<template>
<div class="search-input" @click.stop>
<div
v-if="status.siteStatus === 'focus'"
class="mask"
@click="closeSearchInput"
/>
<div
:class="status.siteStatus === 'focus' ? 'all focus' : 'all'"
:style="{ pointerEvents: inputClickable ? 'none' : 'auto' }"
ref="searchAllRef"
>
<div class="engine" title="切换搜索引擎">
<SvgIcon iconName="icon-baidu" className="baidu" />
</div>
<input
class="input"
ref="searchInputRef"
type="text"
label="search"
title="请输入搜索内容"
:placeholder="inputTip"
v-model="inputValue"
@focus="status.setSiteStatus('focus')"
@keydown="pressKeyboard"
/>
<div class="go" title="搜索" @click="toSearch">
<SvgIcon iconName="icon-search" className="search" />
</div>
</div>
<!-- 搜索建议 -->
<SearchSuggestions ref="searchSuggestionsRef" :keyWord="inputValue" />
</div>
</template>
<script setup>
import { ref, onMounted } from "vue";
import { statusStore, setStore } from "@/stores";
import SearchSuggestions from "@/components/SearchSuggestions.vue";
const set = setStore();
const status = statusStore();
//
const inputTip = import.meta.env.VITE_INPUT_TIP ?? "想要搜点什么";
//
const searchAllRef = ref(null);
const searchInputRef = ref(null);
const inputClickable = ref(true);
const inputValue = ref("");
//
const searchSuggestionsRef = ref(null);
//
const closeSearchInput = () => {
status.setSiteStatus("normal");
inputValue.value = "";
};
//
const toSearch = () => {
const keywords = inputValue.value?.trim();
if (keywords) {
console.log("前往搜索:" + keywords);
} else {
status.setSiteStatus("focus");
searchInputRef.value?.focus();
}
};
// Dom
const searchInputDom = (dom) => {
if (!dom) return false;
dom.addEventListener("animationstart", () => {
console.log("动画开始");
inputClickable.value = true;
});
dom.addEventListener("animationend", () => {
console.log("动画结束");
inputClickable.value = false;
// focus
if (set.autoFocus) {
status.setSiteStatus("focus");
searchInputRef.value?.focus();
}
});
};
//
const pressKeyboard = (event) => {
//
const keyCode = event.keyCode;
// 13
if (keyCode === 13) toSearch();
//
searchSuggestionsRef.value?.keyboardEvents(keyCode);
};
onMounted(() => {
searchInputDom(searchAllRef.value);
});
</script>
<style lang="scss" scoped>
.search-input {
position: relative;
display: flex;
flex-direction: row;
align-items: center;
max-width: 680px;
width: calc(100% - 60px);
.mask {
position: fixed;
top: 0;
left: 0;
width: 100%;
height: 100%;
z-index: 0;
}
.all {
display: flex;
flex-direction: row;
align-items: center;
justify-content: space-between;
height: 42px;
width: 100%;
border-radius: 30px;
color: var(--main-text-color);
background-color: var(--main-background-color);
backdrop-filter: blur(10px);
opacity: 1;
animation: fade-up-in 0.7s cubic-bezier(0.37, 0.99, 0.36, 1);
transition: transform 0.3s, background-color 0.3s;
z-index: 1;
&.focus {
transform: translateY(-50px);
background-color: var(--main-background-hover-color);
.input {
color: var(--main-text-hover-color);
&::placeholder {
opacity: 0;
}
}
.engine,
.go,
.delete {
color: var(--main-text-hover-color);
}
}
.input {
display: flex;
justify-content: center;
height: 100%;
width: 100%;
padding: 0;
margin: 0;
border: none;
outline: none;
background: none;
font-size: 16px;
color: var(--main-text-color);
&::placeholder {
text-align: center;
transform: translateY(1px);
color: var(--main-text-color);
letter-spacing: 2px;
transition: opacity 0.3s;
}
}
.engine,
.go {
cursor: pointer;
display: flex;
align-items: center;
justify-content: center;
height: 100%;
width: 64px;
font-size: 20px;
border-radius: 30px;
transition: background-color 0.3s;
&:hover {
background-color: var(--main-background-color);
}
}
}
}
</style>

View File

@ -0,0 +1,164 @@
<template>
<Transition name="fadeUp">
<div
v-show="
set.showSuggestions &&
status.siteStatus === 'focus' &&
searchKeyword !== null
"
class="search-suggestions"
>
<Transition name="fade" mode="out-in">
<div
v-if="searchKeyword !== null && searchSuggestionsData[0]"
class="all-result"
>
<div
v-for="item in searchSuggestionsData"
:key="item"
class="s-result"
>
<SvgIcon iconName="icon-search" className="search" />
<span class="text">{{ item }}</span>
</div>
</div>
<div class="no-result" v-else-if="!hasSuggestions">
<SvgIcon iconName="icon-found" className="not-found" />
<div class="all-text">
<span class="text">暂无搜索结果</span>
<span class="tip">请尝试其他关键词</span>
</div>
</div>
</Transition>
</div>
</Transition>
</template>
<script setup>
import { ref, watch } from "vue";
import { statusStore, setStore } from "@/stores";
import { getSearchSuggestions } from "@/api";
import debounce from "@/utils/debounce";
const set = setStore();
const status = statusStore();
//
const searchKeyword = ref(null);
//
const searchSuggestionsData = ref([]);
//
const hasSuggestions = ref(true);
//
const props = defineProps({
//
keyWord: {
type: String,
required: true,
},
});
//
const keywordsSearch = debounce((val) => {
if (val?.trim()) {
console.log(val + "的搜索建议");
searchKeyword.value = val;
//
getSearchSuggestions(val).then((res) => {
console.log(res);
//
hasSuggestions.value = res[0] ? true : false;
//
searchSuggestionsData.value = Array.from(res);
});
} else {
searchKeyword.value = null;
hasSuggestions.value = true;
}
}, 500);
//
const keyboardEvents = (keyCode) => {
console.log("键盘按下:" + keyCode);
// 38 / 40
};
//
watch(
() => props.keyWord,
(val) => keywordsSearch(val)
);
//
defineExpose({ keyboardEvents });
</script>
<style lang="scss" scoped>
.search-suggestions {
position: absolute;
top: 0;
left: 0;
width: 100%;
color: var(--main-text-color);
background-color: var(--main-background-light-color);
backdrop-filter: blur(10px);
border-radius: 8px;
.all-result {
.s-result {
cursor: pointer;
box-sizing: border-box;
display: flex;
flex-direction: row;
align-items: center;
padding: 6px 12px;
font-size: 14px;
transition: background-color 0.3s, padding-left 0.3s;
.search {
opacity: 0.8;
margin-right: 8px;
}
.text {
width: 100%;
overflow: hidden;
text-overflow: ellipsis;
white-space: nowrap;
}
&:hover {
background-color: var(--main-background-light-color);
padding-left: 18px;
}
&:first-child {
border-radius: 8px 8px 0 0;
}
&:last-child {
border-radius: 0 0 8px 8px;
}
}
}
.no-result {
width: 100%;
height: 130px;
display: flex;
flex-direction: column;
align-items: center;
justify-content: center;
.not-found {
font-size: 32px;
margin-bottom: 8px;
}
.all-text {
display: flex;
flex-direction: column;
.text {
font-size: 18px;
display: inline-block;
margin-bottom: 6px;
}
.tip {
font-size: 14px;
opacity: 0.8;
}
}
}
}
</style>

View File

View File

@ -0,0 +1,43 @@
<template>
<svg :class="svgClass" aria-hidden="true">
<use :xlink:href="iconClassName" />
</svg>
</template>
<script setup>
import { computed } from "vue";
const props = defineProps({
iconName: {
type: String,
required: true,
},
className: {
type: String,
default: "i-icon",
},
});
// iconfont
const iconClassName = computed(() => {
return `#${props.iconName}`;
});
//
const svgClass = computed(() => {
if (props.className) {
return `i-icon ${props.className}`;
}
return "i-icon";
});
</script>
<style lang="scss">
.i-icon {
width: 1em;
height: 1em;
position: relative;
fill: currentColor;
vertical-align: -2px;
}
</style>

View File

@ -0,0 +1,170 @@
<template>
<div
:class="
status.siteStatus !== 'normal' ? 'weather-time focus' : 'weather-time'
"
>
<div :class="['time', set.timeStyle]">
<span class="hour">{{ timeData.hour ?? "00" }}</span>
<span class="separator">:</span>
<span class="minute">{{ timeData.minute ?? "00" }}</span>
<template v-if="set.showSeconds">
<span class="separator">:</span>
<span class="second">{{ timeData.second ?? "00" }}</span>
</template>
</div>
<div class="date">
<span class="month">{{ timeData.month ?? "0" }}</span>
<span class="day">{{ timeData.day ?? "0" }}</span>
<span class="weekday">{{ timeData.weekday ?? "星期八" }}</span>
</div>
<div v-if="weatherShow" class="weather">
<span class="status">{{ weatherData.condition ?? "N/A" }}</span>
<span class="temperature">{{ weatherData.temp ?? "N/A" }} </span>
<span class="wind">{{ weatherData.windDir ?? "N/A" }}</span>
<span v-if="weatherData.windLevel" class="wind-level">
{{ weatherData.windLevel }}
</span>
</div>
</div>
</template>
<script setup>
import { getCurrentTime } from "@/utils/timeTools";
import { ref, onMounted, onBeforeUnmount } from "vue";
import { statusStore, setStore } from "@/stores";
import { getWeather } from "@/api";
const set = setStore();
const status = statusStore();
//
const timeData = ref({});
const timeInterval = ref(null);
//
const weatherShow = ref(true);
const weatherData = ref({});
//
const updateTimeData = () => {
timeData.value = getCurrentTime();
};
//
const getWeatherData = () => {
//
const currentTime = Date.now();
//
let lastWeatherData = JSON.parse(localStorage.getItem("lastWeatherData")) || {
data: {},
lastFetchTime: 0,
};
//
const timeDifference = currentTime - lastWeatherData.lastFetchTime;
// 2
if (timeDifference >= 2 * 60 * 1000) {
getWeather()
.then((res) => {
console.log(res);
weatherData.value = res.result.condition;
lastWeatherData = {
data: res.result.condition,
lastFetchTime: currentTime,
};
// localStorage
localStorage.setItem(
"lastWeatherData",
JSON.stringify(lastWeatherData)
);
})
.catch((error) => {
console.error("天气获取失败:" + error);
weatherShow.value = false;
});
} else {
console.log("从缓存中读取天气数据");
weatherData.value = lastWeatherData.data;
}
};
onMounted(() => {
//
updateTimeData();
timeInterval.value = setInterval(updateTimeData, 1000);
//
getWeatherData();
});
onBeforeUnmount(() => {
clearInterval(timeInterval.value);
});
</script>
<style lang="scss" scoped>
.weather-time {
position: absolute;
display: flex;
flex-direction: column;
align-items: center;
margin-bottom: 20px;
transform: translateY(-140px);
color: var(--main-text-color);
animation: fade-time-in 0.6s cubic-bezier(0.21, 0.78, 0.36, 1);
transition: transform 0.3s;
&.focus {
transform: translateY(-170px);
}
.time {
cursor: pointer;
font-size: 3rem;
margin: 6px 0px;
text-shadow: var(--main-text-shadow);
transition: transform 0.3s;
.separator {
opacity: 0.8;
font-size: 2.8rem;
display: inline-block;
margin: 0 5px;
transform: translateY(-4px);
animation: separator-breathe 0.7s infinite alternate;
}
&:hover {
transform: scale(1.08);
}
&:active {
transform: scale(1);
}
}
.date {
font-size: 1.15rem;
opacity: 0.8;
margin: 4px 0px;
text-shadow: var(--main-text-shadow);
.month {
&::after {
margin: 0 4px;
content: "月";
}
}
.day {
&::after {
margin: 0 8px 0 4px;
content: "日";
}
}
}
.weather {
margin-top: 6px;
opacity: 0.8;
font-size: 1rem;
text-shadow: var(--main-text-shadow);
.temperature {
margin: 0 6px;
}
.wind-level {
margin-left: 6px;
}
}
}
</style>

23
src/main.js Normal file
View File

@ -0,0 +1,23 @@
import { createApp } from "vue";
// Pinia
import { createPinia } from "pinia";
import piniaPluginPersistedstate from "pinia-plugin-persistedstate";
// IconFont
import SvgIcon from "@/components/SvgIcon.vue";
import "@/utils/iconfont.js";
import App from "@/App.vue";
// 全局样式
import "@/style/global.scss";
const app = createApp(App);
// Pinia
const pinia = createPinia();
pinia.use(piniaPluginPersistedstate);
// 挂载
app.use(pinia);
app.component("SvgIcon", SvgIcon);
app.mount("#app");

6
src/stores/index.js Normal file
View File

@ -0,0 +1,6 @@
// Pinia
import useSetDataStore from "@/stores/setData";
import useStatusDataStore from "@/stores/statusData";
export const setStore = () => useSetDataStore();
export const statusStore = () => useStatusDataStore();

30
src/stores/setData.js Normal file
View File

@ -0,0 +1,30 @@
import { defineStore } from "pinia";
const useSetDataStore = defineStore("setData", {
state: () => {
return {
// 壁纸类别
// 0 本地 / 1 必应 / 2 随机风景 / 3 随机动漫 / 4 自定义
backgroundType: 0,
// 壁纸遮罩
showBackgroundGray: true,
// 清空搜索框
showCleanInput: true,
// 搜索框自动 focus
autoFocus: false,
// 时间样式
timeStyle: "one",
// 是否显秒
showSeconds: false,
// 是否显示搜索建议
showSuggestions: true,
};
},
// 开启数据持久化
persist: {
key: "setData",
storage: window.localStorage,
},
});
export default useSetDataStore;

24
src/stores/statusData.js Normal file
View File

@ -0,0 +1,24 @@
import { defineStore } from "pinia";
const useStatusDataStore = defineStore("statusData", {
state: () => {
return {
// 壁纸状态
imgLoadStatus: false,
// 站点状态
// normal 正常 / focus 搜索 / box 盒子 / set 设置
siteStatus: "normal",
};
},
getters: {},
actions: {
setImgLoadStatus(value) {
this.imgLoadStatus = value;
},
setSiteStatus(value) {
this.siteStatus = value;
},
},
});
export default useStatusDataStore;

131
src/style/global.scss Normal file
View File

@ -0,0 +1,131 @@
:root {
--body-background-color: #333333;
--main-text-color: #ffffff;
--main-text-hover-color: #555555;
--main-background-color: #00000040;
--main-background-light-color: #ffffff30;
--main-background-hover-color: #ffffff;
--main-text-shadow: 0px 0px 8px #00000066;
}
* {
margin: 0;
padding: 0;
user-select: none;
}
html,
body {
width: 100%;
height: 100%;
background-color: var(--body-background-color);
overflow: hidden;
font-family: "HarmonyOS_Regular", sans-serif;
}
#app {
width: 100vw;
height: 100vh;
}
::selection {
color: var(--main-text-color);
background-color: var(--main-text-hover-color);
}
// Transition 动画
.fade-enter-active,
.fade-leave-active {
transition: opacity 0.3s ease;
}
.fade-enter-from,
.fade-leave-to {
opacity: 0;
}
.fadeUp-enter-active,
.fadeUp-leave-active {
transition: opacity 0.3s ease, transform 0.3s ease-in-out;
}
.fadeUp-enter-from,
.fadeUp-leave-to {
opacity: 0;
transform: translateY(10px);
}
.show-enter-active,
.show-leave-active {
transition: opacity 0.25s ease, transform 0.25s ease-in-out;
}
.show-enter-from,
.show-leave-to {
opacity: 0;
transform: scale(0.6);
}
// 全局动画
@keyframes fade-up-in {
0% {
opacity: 0;
}
30% {
opacity: 0;
transform: translateY(30px);
}
100% {
opacity: 1;
transform: translateY(0);
}
}
@keyframes fade-time-in {
0% {
opacity: 0;
}
20% {
opacity: 0;
transform: translateY(-90px);
}
100% {
opacity: 1;
transform: translateY(-140px);
}
}
@keyframes fade-blur-in {
from {
filter: blur(20px) brightness(0.4);
transform: scale(1.2);
}
to {
filter: blur(0) brightness(1);
transform: scale(1);
}
}
@keyframes separator-breathe {
0% {
opacity: 0.8;
}
70% {
opacity: 0.8;
}
100% {
opacity: 0.2;
}
}
@keyframes logo-breathe {
0% {
transform: scale(1);
}
50% {
transform: scale(1.1);
}
100% {
transform: scale(1);
}
}

22
src/utils/debounce.js Normal file
View File

@ -0,0 +1,22 @@
/**
* 防抖函数
* @param {Function} func - 要进行防抖处理的函数
* @param {number} delay - 延迟时间单位毫秒
* @returns {Function} - 返回一个新的函数该函数在指定的时间间隔内最多只会执行一次
*/
const debounce = (func, delay) => {
let timerId;
// 返回一个新的函数
return (...args) => {
// 清除上一个定时器
clearTimeout(timerId);
// 设置新的定时器,在指定的延迟时间后执行函数
timerId = setTimeout(() => {
func.apply(this, args);
}, delay);
};
};
export default debounce;

1
src/utils/iconfont.js Normal file

File diff suppressed because one or more lines are too long

35
src/utils/request.js Normal file
View File

@ -0,0 +1,35 @@
import axios from "axios";
// 全局配置
axios.defaults.timeout = 30000;
axios.defaults.headers.common["X-Requested-With"] = "XMLHttpRequest";
axios.defaults.withCredentials = false;
// 请求拦截
axios.interceptors.request.use(
(request) => {
return request;
},
(error) => {
console.error("请求失败,请稍后重试");
return Promise.reject(error);
}
);
// 响应拦截
axios.interceptors.response.use(
(response) => {
return response.data;
},
(error) => {
if (error.response) {
const data = error.response?.data;
console.error("请求失败,请稍后重试:" + data);
} else {
console.error("请求失败,请稍后重试:" + error);
}
return Promise.reject(error);
}
);
export default axios;

29
src/utils/timeTools.js Normal file
View File

@ -0,0 +1,29 @@
/**
* 获取当前时间
* @returns {Object} 时间对象
*/
export const getCurrentTime = () => {
const time = new Date();
// 格式化
const formatTime = (value) => (value < 10 ? "0" + value : value);
// 处理时间
const year = time.getFullYear();
const month = time.getMonth() + 1;
const day = formatTime(time.getDate());
const hour = formatTime(time.getHours());
const minute = formatTime(time.getMinutes());
const second = formatTime(time.getSeconds());
const weekdayArr = ["日", "一", "二", "三", "四", "五", "六"];
const weekday = "周" + weekdayArr[time.getDay()];
// 返回时间
const currentTime = {
year,
month,
day,
hour,
minute,
second,
weekday,
};
return currentTime;
};

View File

@ -1,12 +0,0 @@
{
"version": 2,
"routes": [{
"handle": "filesystem"
},
{
"src": "/(.*)",
"status": 404,
"dest": "/"
}
]
}

28
vite.config.js Normal file
View File

@ -0,0 +1,28 @@
import { defineConfig } from "vite";
import vue from "@vitejs/plugin-vue";
import path from "path";
// https://vitejs.dev/config/
export default defineConfig({
plugins: [vue()],
server: {
host: "0.0.0.0",
port: 5588,
open: true,
},
resolve: {
// 配置路径别名
alias: {
"@": path.resolve(__dirname, "./src"),
},
},
build: {
minify: "terser",
terserOptions: {
compress: {
// 生产环境时移除 console
pure_funcs: ["console.log"],
},
},
},
});