feat(tray): "Restart to update" item and tooltip (#6)
Build Lotus Chat Desktop / prepare (push) Successful in 6s
Build Lotus Chat Desktop / build-windows (push) Successful in 32m18s
Build Lotus Chat Desktop / build-linux (push) Successful in 39m16s
Build Lotus Chat Desktop / build-arch (push) Successful in 17s
Build Lotus Chat Desktop / update-manifest (push) Successful in 4s
Build Lotus Chat Desktop / prepare (push) Successful in 6s
Build Lotus Chat Desktop / build-windows (push) Successful in 32m18s
Build Lotus Chat Desktop / build-linux (push) Successful in 39m16s
Build Lotus Chat Desktop / build-arch (push) Successful in 17s
Build Lotus Chat Desktop / update-manifest (push) Successful in 4s
`set_tray_update_ready(version | null)` inserts a "Restart to update (vX)" item at the top of the tray menu and sets the tooltip to "Lotus Chat — update ready"; null removes both. The item only exists while an update is pending. Clicking it reveals the window and emits `lotus-tray-install-update`, and cinny runs its normal install flow (progress, retries, failure toast). No icon dot: the unread dot already uses that corner. Bump cinny to 6edfe700 (the web half). Closes #6 Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01PPmy3tPq869XDW4njjVaKA
This commit is contained in:
co-authored by
Claude Opus 5.5
parent
96cdbcd512
commit
687642a096
+1
-1
Submodule cinny updated: d9e7f77402...6edfe70020
@@ -564,6 +564,53 @@ fn set_tray_unread(unread: bool, state: tauri::State<'_, TrayUnreadState>) -> Re
|
||||
state.tray.set_icon(Some(icon)).map_err(|e| e.to_string())
|
||||
}
|
||||
|
||||
/// cinny-desktop #6: the tray's "Restart to update" item. Inserted at the top
|
||||
/// of the menu only while an update is available, so it isn't a dead entry the
|
||||
/// rest of the time.
|
||||
struct TrayUpdateState {
|
||||
menu: Menu<tauri::Wry>,
|
||||
item: MenuItem<tauri::Wry>,
|
||||
shown: std::sync::Mutex<bool>,
|
||||
}
|
||||
|
||||
/// Show (`Some(version)`) or clear (`None`) the tray's update affordance: the
|
||||
/// menu item and the tooltip. The web client drives it from its update status,
|
||||
/// and clicking the item hands the install back to the web flow
|
||||
/// (`lotus-tray-install-update`) so progress and failures are shown in-app.
|
||||
#[tauri::command]
|
||||
fn set_tray_update_ready(app: tauri::AppHandle, version: Option<String>) -> Result<(), String> {
|
||||
let Some(state) = app.try_state::<TrayUpdateState>() else {
|
||||
return Ok(());
|
||||
};
|
||||
let unread = app.try_state::<TrayUnreadState>();
|
||||
let mut shown = state.shown.lock().map_err(|e| e.to_string())?;
|
||||
match version {
|
||||
Some(version) => {
|
||||
state
|
||||
.item
|
||||
.set_text(format!("Restart to update (v{version})"))
|
||||
.map_err(|e| e.to_string())?;
|
||||
if !*shown {
|
||||
state.menu.insert(&state.item, 0).map_err(|e| e.to_string())?;
|
||||
*shown = true;
|
||||
}
|
||||
if let Some(u) = unread {
|
||||
let _ = u.tray.set_tooltip(Some("Lotus Chat — update ready"));
|
||||
}
|
||||
}
|
||||
None => {
|
||||
if *shown {
|
||||
state.menu.remove(&state.item).map_err(|e| e.to_string())?;
|
||||
*shown = false;
|
||||
}
|
||||
if let Some(u) = unread {
|
||||
let _ = u.tray.set_tooltip(Some("Lotus Chat"));
|
||||
}
|
||||
}
|
||||
}
|
||||
Ok(())
|
||||
}
|
||||
|
||||
/// Flash the taskbar button to draw attention (e.g. a new mention while the
|
||||
/// window is unfocused). Clears automatically once the window is focused.
|
||||
#[tauri::command]
|
||||
@@ -611,6 +658,7 @@ pub fn run() {
|
||||
set_badge_count,
|
||||
set_tray_unread,
|
||||
get_tray_dnd,
|
||||
set_tray_update_ready,
|
||||
flash_window,
|
||||
focus_main_window,
|
||||
send_notification,
|
||||
@@ -695,6 +743,12 @@ pub fn run() {
|
||||
.on_menu_event(move |app, event| match event.id.as_ref() {
|
||||
"open" => show_main(app),
|
||||
"quit" => app.exit(0),
|
||||
"update" => {
|
||||
// Show the window so the download progress (and any
|
||||
// failure) is visible; the web side runs the install.
|
||||
show_main(app);
|
||||
native::emit_to_web(app, "lotus-tray-install-update", "{}");
|
||||
}
|
||||
"dnd" => {
|
||||
let checked = dnd_for_event.is_checked().unwrap_or(false);
|
||||
native::emit_to_web(
|
||||
@@ -739,6 +793,12 @@ pub fn run() {
|
||||
// Keep a handle to the DND CheckMenuItem so `get_tray_dnd` can
|
||||
// report its live checkstate for web re-hydration after reload.
|
||||
app.manage(TrayDndState(dnd_item));
|
||||
|
||||
app.manage(TrayUpdateState {
|
||||
menu: tray_menu.clone(),
|
||||
item: MenuItem::with_id(app, "update", "Restart to update", true, None::<&str>)?,
|
||||
shown: std::sync::Mutex::new(false),
|
||||
});
|
||||
} else {
|
||||
eprintln!("tray: no bundled window icon; skipping system tray setup");
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user