feat(front): check update at startup

This commit is contained in:
AkiChase 2024-05-06 19:43:27 +08:00
parent 35e2609db2
commit d07ef6f642
5 changed files with 97 additions and 76 deletions

View File

@ -123,4 +123,10 @@ onMounted(async () => {
.n-scrollbar-content {
height: 100%;
}
.n-spin-content,
.n-spin-container {
width: 100%;
height: 100%;
}
</style>

View File

@ -1,6 +1,6 @@
<script setup lang="ts">
import { onActivated } from "vue";
import { NDialog, useMessage } from "naive-ui";
import { h, onActivated, onMounted } from "vue";
import { NDialog, useDialog, useMessage } from "naive-ui";
import { useGlobalStore } from "../store/global";
import { onBeforeRouteLeave, useRouter } from "vue-router";
import {
@ -11,10 +11,14 @@ import {
updateScreenSizeAndMaskArea,
} from "../hotkey";
import { KeySteeringWheel } from "../keyMappingConfig";
import { getVersion } from "@tauri-apps/api/app";
import { fetch } from "@tauri-apps/plugin-http";
import { open } from "@tauri-apps/plugin-shell";
const store = useGlobalStore();
const router = useRouter();
const message = useMessage();
const dialog = useDialog();
onBeforeRouteLeave(() => {
if (store.controledDevice) {
@ -45,9 +49,54 @@ onActivated(async () => {
}
});
onMounted(() => {
store.checkUpdate = checkUpdate;
checkUpdate();
});
function toStartServer() {
router.replace({ name: "device" });
}
function renderUpdateInfo(content: string) {
const pList = content.split("\r\n").map((line: string) => h("p", line));
return h("div", { style: "margin: 20px 0" }, pList);
}
async function checkUpdate() {
try {
const curVersion = await getVersion();
const res = await fetch(
"https://api.github.com/repos/AkiChase/scrcpy-mask/releases/latest",
{
connectTimeout: 5000,
}
);
if (res.status !== 200) {
message.error("检查更新失败");
} else {
const data = await res.json();
const latestVersion = (data.tag_name as string).slice(1);
if (latestVersion <= curVersion) {
message.success(`最新版本: ${latestVersion},当前已是最新版本`);
return;
}
const body = data.body as string;
dialog.info({
title: `最新版本:${data.tag_name}`,
content: () => renderUpdateInfo(body),
positiveText: "前往发布页",
negativeText: "取消",
onPositiveClick: () => {
open(data.html_url);
},
});
}
} catch (e) {
console.error(e);
message.error("检查更新失败");
}
}
</script>
<template>
@ -184,3 +233,4 @@ function toStartServer() {
}
}
</style>
h, import { getVersion } from "@tauri-apps/api/app";

View File

@ -1,22 +1,11 @@
<script setup lang="ts">
import {
NFlex,
NH4,
NButton,
NIcon,
NP,
useMessage,
useDialog,
} from "naive-ui";
import { NFlex, NH4, NButton, NIcon, NP } from "naive-ui";
import { LogoGithub, Planet } from "@vicons/ionicons5";
import { open } from "@tauri-apps/plugin-shell";
import { fetch } from "@tauri-apps/plugin-http";
import { getVersion } from "@tauri-apps/api/app";
import { h, onMounted, ref } from "vue";
import { onMounted, ref } from "vue";
import { useGlobalStore } from "../../store/global";
const message = useMessage();
const dialog = useDialog();
const store = useGlobalStore();
const appVersion = ref("");
@ -28,46 +17,10 @@ function opendWebsite(url: string) {
open(url);
}
function renderUpdateInfo(content: string) {
const pList = content.split("\r\n").map((line: string) => h("p", line));
return h("div", { style: "margin: 20px 0" }, pList);
}
async function checkUpdate() {
store.showLoading();
try {
const res = await fetch(
"https://api.github.com/repos/AkiChase/scrcpy-mask/releases/latest",
{
connectTimeout: 5000,
}
);
store.hideLoading();
if (res.status !== 200) {
message.error("检查更新失败");
} else {
const data = await res.json();
const latestVersion = (data.tag_name as string).slice(1);
if (latestVersion <= appVersion.value) {
message.success(`最新版本: ${latestVersion},当前已是最新版本`);
return;
}
const body = data.body as string;
dialog.info({
title: `最新版本:${data.tag_name}`,
content: () => renderUpdateInfo(body),
positiveText: "前往发布页",
negativeText: "取消",
onPositiveClick: () => {
opendWebsite(data.html_url);
},
});
}
} catch (e) {
store.hideLoading();
console.error(e);
message.error("检查更新失败");
}
await store.checkUpdate();
store.hideLoading();
}
</script>

View File

@ -3,33 +3,38 @@ import Basic from "./Basic.vue";
import Script from "./Script.vue";
import Mask from "./Mask.vue";
import About from "./About.vue";
import { NTabs, NTabPane, NScrollbar } from "naive-ui";
import { NTabs, NTabPane, NScrollbar, NSpin } from "naive-ui";
import { useGlobalStore } from "../../store/global";
const store = useGlobalStore();
</script>
<template>
<div class="setting">
<NTabs type="line" animated placement="left" default-value="basic">
<NTabPane tab="基本设置" name="basic">
<NScrollbar>
<Basic />
</NScrollbar>
</NTabPane>
<NTabPane tab="蒙版设置" name="mask">
<NScrollbar>
<Mask />
</NScrollbar>
</NTabPane>
<NTabPane tab="脚本设置" name="script">
<NScrollbar>
<Script />
</NScrollbar>
</NTabPane>
<NTabPane tab="关于" name="about">
<NScrollbar>
<About />
</NScrollbar>
</NTabPane>
</NTabs>
<NSpin :show="store.showLoadingRef">
<NTabs type="line" animated placement="left" default-value="basic">
<NTabPane tab="基本设置" name="basic">
<NScrollbar>
<Basic />
</NScrollbar>
</NTabPane>
<NTabPane tab="蒙版设置" name="mask">
<NScrollbar>
<Mask />
</NScrollbar>
</NTabPane>
<NTabPane tab="脚本设置" name="script">
<NScrollbar>
<Script />
</NScrollbar>
</NTabPane>
<NTabPane tab="关于" name="about">
<NScrollbar>
<About />
</NScrollbar>
</NTabPane>
</NTabs>
</NSpin>
</div>
</template>
@ -41,6 +46,10 @@ import { NTabs, NTabPane, NScrollbar } from "naive-ui";
overflow-y: auto;
display: flex;
.n-tabs{
height: 100%;
}
.n-tab-pane {
padding: 0;
}

View File

@ -39,6 +39,8 @@ export const useGlobalStore = defineStore("global", () => {
show: true,
});
let checkUpdate: () => Promise<void> = async () => {};
function applyEditKeyMappingList(): boolean {
const set = new Set<string>();
for (const keyMapping of editKeyMappingList.value) {
@ -91,5 +93,6 @@ export const useGlobalStore = defineStore("global", () => {
applyEditKeyMappingList,
resetEditKeyMappingList,
setKeyMappingIndex,
checkUpdate,
};
});