chore: add update dialog
This commit is contained in:
parent
43160800ce
commit
15eb9424d4
4
bun.lock
4
bun.lock
@ -24,6 +24,7 @@
|
|||||||
"osu-parsers": "4.1.7",
|
"osu-parsers": "4.1.7",
|
||||||
"prettier-plugin-rust": "^0.1.9",
|
"prettier-plugin-rust": "^0.1.9",
|
||||||
"radix-icons-svelte": "1.2.1",
|
"radix-icons-svelte": "1.2.1",
|
||||||
|
"semver": "^7.7.2",
|
||||||
"svelte-confetti": "^2.0.0",
|
"svelte-confetti": "^2.0.0",
|
||||||
},
|
},
|
||||||
"devDependencies": {
|
"devDependencies": {
|
||||||
@ -35,6 +36,7 @@
|
|||||||
"@sveltejs/vite-plugin-svelte": "5.1.0",
|
"@sveltejs/vite-plugin-svelte": "5.1.0",
|
||||||
"@tauri-apps/cli": "2.6.1",
|
"@tauri-apps/cli": "2.6.1",
|
||||||
"@types/crypto-js": "^4.2.2",
|
"@types/crypto-js": "^4.2.2",
|
||||||
|
"@types/semver": "^7.7.0",
|
||||||
"autoprefixer": "10.4.21",
|
"autoprefixer": "10.4.21",
|
||||||
"bits-ui": "^1.4.7",
|
"bits-ui": "^1.4.7",
|
||||||
"clsx": "2.1.1",
|
"clsx": "2.1.1",
|
||||||
@ -286,6 +288,8 @@
|
|||||||
|
|
||||||
"@types/node": ["@types/node@20.19.1", "", { "dependencies": { "undici-types": "~6.21.0" } }, "sha512-jJD50LtlD2dodAEO653i3YF04NWak6jN3ky+Ri3Em3mGR39/glWiboM/IePaRbgwSfqM1TpGXfAg8ohn/4dTgA=="],
|
"@types/node": ["@types/node@20.19.1", "", { "dependencies": { "undici-types": "~6.21.0" } }, "sha512-jJD50LtlD2dodAEO653i3YF04NWak6jN3ky+Ri3Em3mGR39/glWiboM/IePaRbgwSfqM1TpGXfAg8ohn/4dTgA=="],
|
||||||
|
|
||||||
|
"@types/semver": ["@types/semver@7.7.0", "", {}, "sha512-k107IF4+Xr7UHjwDc7Cfd6PRQfbdkiRabXGRjo07b4WyPahFBZCZ1sE+BNxYIJPPg73UkfOsVOLwqVc/6ETrIA=="],
|
||||||
|
|
||||||
"@typescript-eslint/eslint-plugin": ["@typescript-eslint/eslint-plugin@8.35.1", "", { "dependencies": { "@eslint-community/regexpp": "^4.10.0", "@typescript-eslint/scope-manager": "8.35.1", "@typescript-eslint/type-utils": "8.35.1", "@typescript-eslint/utils": "8.35.1", "@typescript-eslint/visitor-keys": "8.35.1", "graphemer": "^1.4.0", "ignore": "^7.0.0", "natural-compare": "^1.4.0", "ts-api-utils": "^2.1.0" }, "peerDependencies": { "@typescript-eslint/parser": "^8.35.1", "eslint": "^8.57.0 || ^9.0.0", "typescript": ">=4.8.4 <5.9.0" } }, "sha512-9XNTlo7P7RJxbVeICaIIIEipqxLKguyh+3UbXuT2XQuFp6d8VOeDEGuz5IiX0dgZo8CiI6aOFLg4e8cF71SFVg=="],
|
"@typescript-eslint/eslint-plugin": ["@typescript-eslint/eslint-plugin@8.35.1", "", { "dependencies": { "@eslint-community/regexpp": "^4.10.0", "@typescript-eslint/scope-manager": "8.35.1", "@typescript-eslint/type-utils": "8.35.1", "@typescript-eslint/utils": "8.35.1", "@typescript-eslint/visitor-keys": "8.35.1", "graphemer": "^1.4.0", "ignore": "^7.0.0", "natural-compare": "^1.4.0", "ts-api-utils": "^2.1.0" }, "peerDependencies": { "@typescript-eslint/parser": "^8.35.1", "eslint": "^8.57.0 || ^9.0.0", "typescript": ">=4.8.4 <5.9.0" } }, "sha512-9XNTlo7P7RJxbVeICaIIIEipqxLKguyh+3UbXuT2XQuFp6d8VOeDEGuz5IiX0dgZo8CiI6aOFLg4e8cF71SFVg=="],
|
||||||
|
|
||||||
"@typescript-eslint/parser": ["@typescript-eslint/parser@8.35.1", "", { "dependencies": { "@typescript-eslint/scope-manager": "8.35.1", "@typescript-eslint/types": "8.35.1", "@typescript-eslint/typescript-estree": "8.35.1", "@typescript-eslint/visitor-keys": "8.35.1", "debug": "^4.3.4" }, "peerDependencies": { "eslint": "^8.57.0 || ^9.0.0", "typescript": ">=4.8.4 <5.9.0" } }, "sha512-3MyiDfrfLeK06bi/g9DqJxP5pV74LNv4rFTyvGDmT3x2p1yp1lOd+qYZfiRPIOf/oON+WRZR5wxxuF85qOar+w=="],
|
"@typescript-eslint/parser": ["@typescript-eslint/parser@8.35.1", "", { "dependencies": { "@typescript-eslint/scope-manager": "8.35.1", "@typescript-eslint/types": "8.35.1", "@typescript-eslint/typescript-estree": "8.35.1", "@typescript-eslint/visitor-keys": "8.35.1", "debug": "^4.3.4" }, "peerDependencies": { "eslint": "^8.57.0 || ^9.0.0", "typescript": ">=4.8.4 <5.9.0" } }, "sha512-3MyiDfrfLeK06bi/g9DqJxP5pV74LNv4rFTyvGDmT3x2p1yp1lOd+qYZfiRPIOf/oON+WRZR5wxxuF85qOar+w=="],
|
||||||
|
@ -38,6 +38,7 @@
|
|||||||
"osu-parsers": "4.1.7",
|
"osu-parsers": "4.1.7",
|
||||||
"prettier-plugin-rust": "^0.1.9",
|
"prettier-plugin-rust": "^0.1.9",
|
||||||
"radix-icons-svelte": "1.2.1",
|
"radix-icons-svelte": "1.2.1",
|
||||||
|
"semver": "^7.7.2",
|
||||||
"svelte-confetti": "^2.0.0"
|
"svelte-confetti": "^2.0.0"
|
||||||
},
|
},
|
||||||
"devDependencies": {
|
"devDependencies": {
|
||||||
@ -49,6 +50,7 @@
|
|||||||
"@sveltejs/vite-plugin-svelte": "5.1.0",
|
"@sveltejs/vite-plugin-svelte": "5.1.0",
|
||||||
"@tauri-apps/cli": "2.6.1",
|
"@tauri-apps/cli": "2.6.1",
|
||||||
"@types/crypto-js": "^4.2.2",
|
"@types/crypto-js": "^4.2.2",
|
||||||
|
"@types/semver": "^7.7.0",
|
||||||
"autoprefixer": "10.4.21",
|
"autoprefixer": "10.4.21",
|
||||||
"bits-ui": "^1.4.7",
|
"bits-ui": "^1.4.7",
|
||||||
"clsx": "2.1.1",
|
"clsx": "2.1.1",
|
||||||
|
2
src-tauri/Cargo.lock
generated
2
src-tauri/Cargo.lock
generated
@ -1081,7 +1081,7 @@ dependencies = [
|
|||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "ezpplauncher"
|
name = "ezpplauncher"
|
||||||
version = "0.1.0"
|
version = "3.0.0-beta.1"
|
||||||
dependencies = [
|
dependencies = [
|
||||||
"hardware-id",
|
"hardware-id",
|
||||||
"md5",
|
"md5",
|
||||||
|
@ -1,8 +1,8 @@
|
|||||||
[package]
|
[package]
|
||||||
name = "ezpplauncher"
|
name = "ezpplauncher"
|
||||||
version = "0.1.0"
|
version = "3.0.0-beta.1"
|
||||||
description = "A Tauri App"
|
description = "EZPPLauncher redefined."
|
||||||
authors = ["you"]
|
authors = ["HorizonCode"]
|
||||||
edition = "2024"
|
edition = "2024"
|
||||||
|
|
||||||
# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html
|
# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html
|
||||||
|
@ -16,6 +16,11 @@ use crate::utils::{
|
|||||||
set_osu_config_vals, set_osu_user_config_vals,
|
set_osu_config_vals, set_osu_user_config_vals,
|
||||||
};
|
};
|
||||||
|
|
||||||
|
#[tauri::command]
|
||||||
|
pub fn get_launcher_version() -> String {
|
||||||
|
env!("CARGO_PKG_VERSION").to_string()
|
||||||
|
}
|
||||||
|
|
||||||
#[tauri::command]
|
#[tauri::command]
|
||||||
pub fn get_hwid() -> String {
|
pub fn get_hwid() -> String {
|
||||||
let hwid = get_id().unwrap();
|
let hwid = get_id().unwrap();
|
||||||
@ -624,3 +629,8 @@ pub fn is_osu_running() -> bool {
|
|||||||
pub fn open_url_in_browser(url: String) -> Result<(), String> {
|
pub fn open_url_in_browser(url: String) -> Result<(), String> {
|
||||||
open::that(&url).map_err(|e| format!("Failed to open URL: {}", e))
|
open::that(&url).map_err(|e| format!("Failed to open URL: {}", e))
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[tauri::command]
|
||||||
|
pub fn exit(app: AppHandle) {
|
||||||
|
app.exit(0x0100);
|
||||||
|
}
|
||||||
|
@ -4,10 +4,11 @@ use tauri::Manager;
|
|||||||
pub mod commands;
|
pub mod commands;
|
||||||
pub mod utils;
|
pub mod utils;
|
||||||
use crate::commands::{
|
use crate::commands::{
|
||||||
download_ezpp_launcher_update_files, find_osu_installation, get_beatmapsets_count,
|
download_ezpp_launcher_update_files, exit, find_osu_installation, get_beatmapsets_count,
|
||||||
get_ezpp_launcher_update_files, get_hwid, get_osu_release_stream, get_osu_skin,
|
get_ezpp_launcher_update_files, get_hwid, get_launcher_version, get_osu_release_stream,
|
||||||
get_osu_version, get_skins_count, is_osu_running, open_url_in_browser, replace_ui_files,
|
get_osu_skin, get_osu_version, get_skins_count, is_osu_running, open_url_in_browser,
|
||||||
run_osu, run_osu_updater, set_osu_config_values, set_osu_user_config_values, valid_osu_folder,
|
replace_ui_files, run_osu, run_osu_updater, set_osu_config_values, set_osu_user_config_values,
|
||||||
|
valid_osu_folder,
|
||||||
};
|
};
|
||||||
|
|
||||||
#[cfg_attr(mobile, tauri::mobile_entry_point)]
|
#[cfg_attr(mobile, tauri::mobile_entry_point)]
|
||||||
@ -42,7 +43,9 @@ pub fn run() {
|
|||||||
download_ezpp_launcher_update_files,
|
download_ezpp_launcher_update_files,
|
||||||
replace_ui_files,
|
replace_ui_files,
|
||||||
is_osu_running,
|
is_osu_running,
|
||||||
open_url_in_browser
|
open_url_in_browser,
|
||||||
|
get_launcher_version,
|
||||||
|
exit
|
||||||
])
|
])
|
||||||
.plugin(tauri_plugin_fs::init())
|
.plugin(tauri_plugin_fs::init())
|
||||||
.plugin(tauri_plugin_dialog::init())
|
.plugin(tauri_plugin_dialog::init())
|
||||||
|
33
src/lib/api/git.ts
Normal file
33
src/lib/api/git.ts
Normal file
@ -0,0 +1,33 @@
|
|||||||
|
import type { Release } from '@/types';
|
||||||
|
import { betterFetch } from '@better-fetch/fetch';
|
||||||
|
import semver from 'semver';
|
||||||
|
|
||||||
|
const ENDPOINT = 'https://git.ez-pp.farm/';
|
||||||
|
|
||||||
|
const timeout = 5000; // 5 seconds;
|
||||||
|
|
||||||
|
export const git = {
|
||||||
|
hasUpdate: async (version: string): Promise<Release | undefined> => {
|
||||||
|
try {
|
||||||
|
const request = await betterFetch<Release[]>(
|
||||||
|
`${ENDPOINT}api/v1/repos/EZPPFarm/EZPPLauncher/releases?limit=1`,
|
||||||
|
{
|
||||||
|
timeout,
|
||||||
|
headers: {
|
||||||
|
'User-Agent': 'EZPPLauncher',
|
||||||
|
},
|
||||||
|
}
|
||||||
|
);
|
||||||
|
if (request.error) return undefined;
|
||||||
|
|
||||||
|
const latestRelease = request.data[0];
|
||||||
|
if (!latestRelease) return undefined;
|
||||||
|
|
||||||
|
const hasUpdate = semver.lt(version, latestRelease.tag_name);
|
||||||
|
|
||||||
|
return hasUpdate ? latestRelease : undefined;
|
||||||
|
} catch {
|
||||||
|
return undefined;
|
||||||
|
}
|
||||||
|
},
|
||||||
|
};
|
@ -6,6 +6,8 @@
|
|||||||
|
|
||||||
import { getCurrentWindow } from '@tauri-apps/api/window';
|
import { getCurrentWindow } from '@tauri-apps/api/window';
|
||||||
import { onMount } from 'svelte';
|
import { onMount } from 'svelte';
|
||||||
|
import { launcherVersion } from '@/global';
|
||||||
|
import Badge from '../badge/badge.svelte';
|
||||||
|
|
||||||
onMount(() => {
|
onMount(() => {
|
||||||
const appWindow = getCurrentWindow();
|
const appWindow = getCurrentWindow();
|
||||||
@ -18,9 +20,10 @@
|
|||||||
</script>
|
</script>
|
||||||
|
|
||||||
<div data-tauri-drag-region class="titlebar z-[60] border-b border-theme-800/90">
|
<div data-tauri-drag-region class="titlebar z-[60] border-b border-theme-800/90">
|
||||||
<div class="mr-auto ms-2 flex flex-row gap-2 items-center text-[1.05rem] font-semibold">
|
<div class="mr-auto ms-2 flex flex-row gap-2 items-center text-[1.05rem] font-semibold pointer-events-none">
|
||||||
<img src={Logo} alt="EZPP Launcher Logo" class="h-11 w-11 inline-block" />
|
<img src={Logo} alt="EZPP Launcher Logo" class="h-11 w-11 inline-block" />
|
||||||
<span>EZPPLauncher</span>
|
<span>EZPPLauncher</span>
|
||||||
|
<Badge class="!text-[0.6rem] py-[0.5px] bg-primary-500 hover:bg-primary-500">{$launcherVersion}</Badge>
|
||||||
</div>
|
</div>
|
||||||
<div class="titlebar-button rounded-lg transition-colors duration-75" id="titlebar-minimize">
|
<div class="titlebar-button rounded-lg transition-colors duration-75" id="titlebar-minimize">
|
||||||
<Minimize size={18} />
|
<Minimize size={18} />
|
||||||
|
@ -2,9 +2,13 @@ import { writable } from 'svelte/store';
|
|||||||
import { ezppfarm } from './api/ezpp';
|
import { ezppfarm } from './api/ezpp';
|
||||||
import type { Component } from 'svelte';
|
import type { Component } from 'svelte';
|
||||||
import Loading from '../pages/Loading.svelte';
|
import Loading from '../pages/Loading.svelte';
|
||||||
|
import type { Release } from './types';
|
||||||
|
|
||||||
export const currentView = writable<Component>(Loading);
|
export const currentView = writable<Component>(Loading);
|
||||||
|
|
||||||
|
export const launcherVersion = writable<string>('');
|
||||||
|
export const newVersion = writable<Release | undefined>(undefined);
|
||||||
|
|
||||||
export const currentLoadingInfo = writable<string>('Initializing...');
|
export const currentLoadingInfo = writable<string>('Initializing...');
|
||||||
|
|
||||||
export const firstStartup = writable<boolean>(false);
|
export const firstStartup = writable<boolean>(false);
|
||||||
|
@ -110,3 +110,6 @@ export const isOsuRunning = async () => {
|
|||||||
const result = await invoke('is_osu_running');
|
const result = await invoke('is_osu_running');
|
||||||
return typeof result === 'boolean' ? result : false;
|
return typeof result === 'boolean' ? result : false;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
export const getLauncherVersion = async () => await invoke<string>('get_launcher_version');
|
||||||
|
export const exit = async () => await invoke('exit');
|
||||||
|
@ -134,3 +134,54 @@ export type UpdateStatus = {
|
|||||||
size: number;
|
size: number;
|
||||||
progress: number;
|
progress: number;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
export type Release = {
|
||||||
|
id: number;
|
||||||
|
tag_name: string;
|
||||||
|
target_commitish: string;
|
||||||
|
name: string;
|
||||||
|
body: string;
|
||||||
|
url: string;
|
||||||
|
html_url: string;
|
||||||
|
tarball_url: string;
|
||||||
|
zipball_url: string;
|
||||||
|
upload_url: string;
|
||||||
|
draft: boolean;
|
||||||
|
prerelease: boolean;
|
||||||
|
created_at: Date;
|
||||||
|
published_at: Date;
|
||||||
|
author: {
|
||||||
|
id: number;
|
||||||
|
login: string;
|
||||||
|
login_name: string;
|
||||||
|
source_id: number;
|
||||||
|
full_name: string;
|
||||||
|
email: string;
|
||||||
|
avatar_url: string;
|
||||||
|
html_url: string;
|
||||||
|
language: string;
|
||||||
|
is_admin: boolean;
|
||||||
|
last_login: Date;
|
||||||
|
created: Date;
|
||||||
|
restricted: boolean;
|
||||||
|
active: boolean;
|
||||||
|
prohibit_login: boolean;
|
||||||
|
location: string;
|
||||||
|
website: string;
|
||||||
|
description: string;
|
||||||
|
visibility: string;
|
||||||
|
followers_count: number;
|
||||||
|
following_count: number;
|
||||||
|
starred_repos_count: number;
|
||||||
|
username: string;
|
||||||
|
};
|
||||||
|
assets: {
|
||||||
|
id: number;
|
||||||
|
name: string;
|
||||||
|
size: number;
|
||||||
|
download_count: number;
|
||||||
|
created_at: Date;
|
||||||
|
uuid: string;
|
||||||
|
browser_download_url: string;
|
||||||
|
}[];
|
||||||
|
};
|
||||||
|
@ -7,6 +7,8 @@
|
|||||||
currentSkin,
|
currentSkin,
|
||||||
currentView,
|
currentView,
|
||||||
firstStartup,
|
firstStartup,
|
||||||
|
launcherVersion,
|
||||||
|
newVersion,
|
||||||
osuBuild,
|
osuBuild,
|
||||||
osuStream,
|
osuStream,
|
||||||
skins,
|
skins,
|
||||||
@ -34,6 +36,7 @@
|
|||||||
getVersion,
|
getVersion,
|
||||||
isValidOsuFolder,
|
isValidOsuFolder,
|
||||||
} from '@/osuUtil';
|
} from '@/osuUtil';
|
||||||
|
import { git } from '@/api/git';
|
||||||
|
|
||||||
let ezppLogo: HTMLImageElement;
|
let ezppLogo: HTMLImageElement;
|
||||||
let spinnerCircle: SVGCircleElement;
|
let spinnerCircle: SVGCircleElement;
|
||||||
@ -139,6 +142,12 @@
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
currentLoadingInfo.set('Checking for EZPPLauncher updates...');
|
||||||
|
const launcherUpdate = await git.hasUpdate($launcherVersion);
|
||||||
|
if (launcherUpdate) {
|
||||||
|
newVersion.set(launcherUpdate);
|
||||||
|
}
|
||||||
|
|
||||||
animate(ezppLogo, {
|
animate(ezppLogo, {
|
||||||
opacity: [1, 0],
|
opacity: [1, 0],
|
||||||
scale: [1, 1.05],
|
scale: [1, 1.05],
|
||||||
|
@ -1,7 +1,15 @@
|
|||||||
<script lang="ts">
|
<script lang="ts">
|
||||||
import '../app.css';
|
import '../app.css';
|
||||||
|
import Logo from '$assets/logo.png';
|
||||||
|
|
||||||
import Titlebar from '@/components/ui/titlebar/titlebar.svelte';
|
import Titlebar from '@/components/ui/titlebar/titlebar.svelte';
|
||||||
import { currentLoadingInfo, firstStartup, setupValues } from '@/global';
|
import {
|
||||||
|
currentLoadingInfo,
|
||||||
|
firstStartup,
|
||||||
|
launcherVersion,
|
||||||
|
newVersion,
|
||||||
|
setupValues,
|
||||||
|
} from '@/global';
|
||||||
import { onMount } from 'svelte';
|
import { onMount } from 'svelte';
|
||||||
import OsuCursor from '@/components/ui/osu-cursor/OsuCursor.svelte';
|
import OsuCursor from '@/components/ui/osu-cursor/OsuCursor.svelte';
|
||||||
import {
|
import {
|
||||||
@ -15,9 +23,14 @@
|
|||||||
import { Buffer } from 'buffer';
|
import { Buffer } from 'buffer';
|
||||||
import { Toaster } from '@/components/ui/sonner';
|
import { Toaster } from '@/components/ui/sonner';
|
||||||
import { userAuth } from '@/userAuthentication';
|
import { userAuth } from '@/userAuthentication';
|
||||||
|
import * as AlertDialog from '@/components/ui/alert-dialog';
|
||||||
|
import { exit, getLauncherVersion } from '@/osuUtil';
|
||||||
|
|
||||||
import '@fontsource/sora';
|
import '@fontsource/sora';
|
||||||
import '@fontsource/space-mono';
|
import '@fontsource/space-mono';
|
||||||
|
import { ArrowRight } from 'lucide-svelte';
|
||||||
|
import Button from '@/components/ui/button/button.svelte';
|
||||||
|
import { openURL } from '@/utils';
|
||||||
|
|
||||||
let { children } = $props();
|
let { children } = $props();
|
||||||
|
|
||||||
@ -71,8 +84,10 @@
|
|||||||
|
|
||||||
onMount(async () => {
|
onMount(async () => {
|
||||||
window.Buffer = Buffer;
|
window.Buffer = Buffer;
|
||||||
|
|
||||||
disableReload();
|
disableReload();
|
||||||
setupValues();
|
setupValues();
|
||||||
|
launcherVersion.set(await getLauncherVersion());
|
||||||
const isFirstStartup = await $userSettings.init();
|
const isFirstStartup = await $userSettings.init();
|
||||||
$userAuth.init();
|
$userAuth.init();
|
||||||
|
|
||||||
@ -105,6 +120,43 @@
|
|||||||
<Toaster richColors closeButton />
|
<Toaster richColors closeButton />
|
||||||
|
|
||||||
<Titlebar />
|
<Titlebar />
|
||||||
|
|
||||||
|
<AlertDialog.Root open={$newVersion !== undefined}>
|
||||||
|
<AlertDialog.Content class="bg-theme-950 border-theme-800 p-0">
|
||||||
|
<div
|
||||||
|
class="flex flex-col items-center justify-center border-b border-theme-800 bg-black/40 rounded-t-lg p-3"
|
||||||
|
>
|
||||||
|
<img class="h-20 w-20" src={Logo} alt="logo" />
|
||||||
|
<span class="font-semibold text-xl">Update available!</span>
|
||||||
|
</div>
|
||||||
|
<div
|
||||||
|
class="grid grid-cols-3 items-center bg-theme-900 border border-theme-800 rounded-lg mx-3 p-3"
|
||||||
|
>
|
||||||
|
<div class="flex flex-col items-center justify-center">
|
||||||
|
<span class="text-sm text-muted-foreground">Current Version</span>
|
||||||
|
<span>{$launcherVersion}</span>
|
||||||
|
</div>
|
||||||
|
<div class="flex items-center justify-center">
|
||||||
|
<ArrowRight />
|
||||||
|
</div>
|
||||||
|
<div class="flex flex-col items-center justify-center">
|
||||||
|
<span class="text-sm text-muted-foreground">New Version</span>
|
||||||
|
<span class="text-green-400">{$newVersion?.tag_name}</span>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div class="flex items-center justify-center mb-3">
|
||||||
|
<Button
|
||||||
|
onclick={async () => {
|
||||||
|
if ($newVersion) {
|
||||||
|
await openURL($newVersion.html_url);
|
||||||
|
await exit();
|
||||||
|
}
|
||||||
|
}}>Update now</Button
|
||||||
|
>
|
||||||
|
</div>
|
||||||
|
</AlertDialog.Content>
|
||||||
|
</AlertDialog.Root>
|
||||||
|
|
||||||
<main>
|
<main>
|
||||||
{@render children()}
|
{@render children()}
|
||||||
</main>
|
</main>
|
||||||
|
Loading…
x
Reference in New Issue
Block a user