You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Mac平台基于GPUI的Rust应用关闭主窗口后无法退出问题

GPUI 0.2.2应用关闭主窗口后进程无法退出(macOS)

问题重现

使用GPUI 0.2.2开发Rust UI应用,在macOS 12.7.6环境下,点击主窗口关闭按钮后,窗口消失但应用进程仍在后台运行,无法自动退出。

环境信息:

  • macOS 12.7.6,16GB内存
  • Xcode 14.2
  • Rust/Cargo 1.95.0
  • GPUI 0.2.2

原实现代码:

use gpui::{
    div, prelude::*, px, rgb, size, App, Application, Bounds, Context, SharedString, Window,
    WindowBounds, WindowOptions,
};
 
struct HelloWorld {
    text: SharedString,
}
 
impl Render for HelloWorld {
    fn render(&mut self, _window: &mut Window, _cx: &mut Context<Self>) -> impl IntoElement {
        div()
            .flex()
            .flex_col()
            .gap_3()
            .bg(rgb(0x505050))
            .size(px(500.0))
            .justify_center()
            .items_center()
            .shadow_lg()
            .border_1()
            .border_color(rgb(0x0000ff))
            .text_xl()
            .text_color(rgb(0xffffff))
            .child(format!("Hello, {}!", &self.text))
            .child(
                div()
                    .flex()
                    .gap_2()
                    .child(div().size_8().bg(gpui::red()))
                    .child(div().size_8().bg(gpui::green()))
                    .child(div().size_8().bg(gpui::blue()))
                    .child(div().size_8().bg(gpui::yellow()))
                    .child(div().size_8().bg(gpui::black()))
                    .child(div().size_8().bg(gpui::white())),
            )
    }
}
 
fn main() {
    Application::new().run(|cx: &mut App| {
        let bounds = Bounds::centered(None, size(px(500.), px(500.0)), cx);
        cx.open_window(
            WindowOptions {
                window_bounds: Some(WindowBounds::Windowed(bounds)),
                ..Default::default()
            },
            |_, cx| {
                cx.new(|_| HelloWorld {
                    text: "World".into(),
                })
            },
        )
        .unwrap();
    });
}

Cargo.toml配置:

[package]
name = "gpui_test"
version = "0.1.0"
edition = "2024"

[dependencies]
gpui = "0.2.2"

原因分析

GPUI框架的默认行为中,关闭单个窗口不会自动触发应用退出——因为框架支持多窗口场景,关闭某一个窗口不代表要终止整个应用进程。因此需要手动监听窗口关闭事件,显式触发退出逻辑。

解决方案

在窗口创建后,订阅窗口的WillClose事件,在事件触发时调用cx.quit()终止应用进程。

修改后的代码

首先补充导入WillClose事件:

use gpui::{
    div, prelude::*, px, rgb, size, App, Application, Bounds, Context, SharedString, Window,
    WindowBounds, WindowOptions, WillClose, // 新增事件导入
};

然后修改main函数,添加事件监听:

fn main() {
    Application::new().run(|cx: &mut App| {
        let bounds = Bounds::centered(None, size(px(500.), px(500.0)), cx);
        let window = cx.open_window(
            WindowOptions {
                window_bounds: Some(WindowBounds::Windowed(bounds)),
                ..Default::default()
            },
            |_, cx| {
                cx.new(|_| HelloWorld {
                    text: "World".into(),
                })
            },
        )
        .unwrap();

        // 监听窗口关闭事件,触发时退出应用
        cx.subscribe(&window, move |_event: &WillClose, cx| {
            cx.quit();
        });
    });
}

验证效果

修改代码后重新编译运行,点击窗口关闭按钮,窗口消失的同时应用进程会正常退出,不会在后台残留。

内容的提问来源于stack exchange,提问作者long

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.02 06:12:29