diff --git a/backend/storage/preferences.go b/backend/storage/preferences.go index 6726672..6d678b8 100644 --- a/backend/storage/preferences.go +++ b/backend/storage/preferences.go @@ -27,6 +27,8 @@ func (p *PreferencesStorage) DefaultPreferences() map[string]any { "use_sys_proxy": false, "use_sys_proxy_http": false, "check_update": true, + "skip_version": "", + "aside_width": 300, }, "editor": map[string]any{ "font": "", diff --git a/frontend/src/langs/en.json b/frontend/src/langs/en.json index 4caf30c..169da8b 100644 --- a/frontend/src/langs/en.json +++ b/frontend/src/langs/en.json @@ -175,8 +175,12 @@ "title": "Set Key TTL" }, "upgrade": { + "title": "New Version Available", "new_version_tip": "A new version({ver}) is available. Download now?", - "no_update": "You're update to date" + "no_update": "You're update to date", + "download_now": "Download", + "later": "Later", + "skip": "Skip This Update" } }, "menu": { diff --git a/frontend/src/langs/zh-cn.json b/frontend/src/langs/zh-cn.json index beddec3..2dd0761 100644 --- a/frontend/src/langs/zh-cn.json +++ b/frontend/src/langs/zh-cn.json @@ -176,8 +176,12 @@ "title": "设置键存活时间" }, "upgrade":{ - "new_version_tip": "有可用的新版本({ver}),是否立即下载", - "no_update": "当前已是最新版" + "title": "有可用新版本", + "new_version_tip": "新版本({ver}),是否立即下载", + "no_update": "当前已是最新版", + "download_now": "立即下载", + "later": "稍后提醒我", + "skip": "忽略本次更新" } }, "menu": { diff --git a/frontend/src/stores/preferences.js b/frontend/src/stores/preferences.js index 2e19e64..6345290 100644 --- a/frontend/src/stores/preferences.js +++ b/frontend/src/stores/preferences.js @@ -10,7 +10,8 @@ import { } from 'wailsjs/go/services/preferencesService.js' import { BrowserOpenURL } from 'wailsjs/runtime/runtime.js' import { i18nGlobal } from '@/utils/i18n.js' -import { enUS, useOsTheme, zhCN } from 'naive-ui' +import { enUS, NButton, NSpace, useOsTheme, zhCN } from 'naive-ui' +import { h, nextTick } from 'vue' const osTheme = useOsTheme() const usePreferencesStore = defineStore('preferences', { @@ -38,6 +39,7 @@ const usePreferencesStore = defineStore('preferences', { useSysProxy: false, useSysProxyHttp: false, checkUpdate: false, + skipVersion: '', asideWidth: 300, }, editor: { @@ -251,10 +253,49 @@ const usePreferencesStore = defineStore('preferences', { const { success, data = {} } = await CheckForUpdate() if (success) { const { version = 'v1.0.0', latest, page_url: pageUrl } = data - if (latest > version && !isEmpty(pageUrl)) { - const tip = i18nGlobal.t('dialogue.upgrade.new_version_tip', { ver: version }) - $dialog.warning(tip, () => { - BrowserOpenURL(pageUrl) + if ((manual || latest > this.general.skipVersion) && latest > version && !isEmpty(pageUrl)) { + const notiRef = $notification.show({ + title: i18nGlobal.t('dialogue.upgrade.title'), + content: i18nGlobal.t('dialogue.upgrade.new_version_tip', { ver: latest }), + action: () => + h('div', { class: 'flex-box-h flex-item-expand' }, [ + h(NSpace, { wrapItem: false }, () => [ + h( + NButton, + { + size: 'small', + secondary: true, + onClick: () => { + // skip this update + this.general.skipVersion = latest + this.savePreferences() + notiRef.destroy() + }, + }, + () => i18nGlobal.t('dialogue.upgrade.skip'), + ), + h( + NButton, + { + size: 'small', + secondary: true, + onClick: notiRef.destroy, + }, + () => i18nGlobal.t('dialogue.upgrade.later'), + ), + h( + NButton, + { + type: 'primary', + size: 'small', + secondary: true, + onClick: () => BrowserOpenURL(pageUrl), + }, + () => i18nGlobal.t('dialogue.upgrade.download_now'), + ), + ]), + ]), + onPositiveClick: () => BrowserOpenURL(pageUrl), }) return } @@ -264,10 +305,12 @@ const usePreferencesStore = defineStore('preferences', { $message.info(i18nGlobal.t('dialogue.upgrade.no_update')) } } finally { - if (msgRef != null) { - msgRef.destroy() - msgRef = null - } + nextTick().then(() => { + if (msgRef != null) { + msgRef.destroy() + msgRef = null + } + }) } }, }, diff --git a/frontend/src/utils/discrete.js b/frontend/src/utils/discrete.js index b502b4f..dfd56de 100644 --- a/frontend/src/utils/discrete.js +++ b/frontend/src/utils/discrete.js @@ -1,5 +1,5 @@ import usePreferencesStore from 'stores/preferences.js' -import { createDiscreteApi, darkTheme } from 'naive-ui' +import { createDiscreteApi, darkTheme, useDialog } from 'naive-ui' import { themeOverrides } from '@/utils/theme.js' import { i18nGlobal } from '@/utils/i18n.js' import { computed } from 'vue' @@ -28,6 +28,13 @@ function setupMessage(message) { function setupNotification(notification) { return { + /** + * @param {NotificationOption} option + * @return {NotificationReactive} + */ + show(option) { + return notification.create(option) + }, error: (content, option = {}) => { option.content = content option.title = option.title || i18nGlobal.t('common.error') @@ -50,8 +57,23 @@ function setupNotification(notification) { } } +/** + * + * @param {DialogApiInjection} dialog + * @return {*} + */ function setupDialog(dialog) { return { + /** + * @param {DialogOptions} option + * @return {DialogReactive} + */ + show(option) { + option.closable = option.closable === true + option.autoFocus = option.autoFocus === true + option.transformOrigin = 'center' + return dialog.create(option) + }, warning: (content, onConfirm) => { return dialog.warning({ title: i18nGlobal.t('common.warning'), @@ -86,7 +108,7 @@ export async function setupDiscreteApi() { }, notificationProviderProps: { max: 5, - placement: 'top-right', + placement: 'bottom-right', keepAliveOnHover: true, }, })