Winit 示例窗口未在 WSL2 上打开

Winit example window not opening on WSL2

提问人:Cosimos Cendo 提问时间:11/1/2023 最后编辑:cafce25Cosimos Cendo 更新时间:11/2/2023 访问量:88

问:

我的最终目标是在 WSL 中使用 Pixels 在 Rust 中创建数据可视化。

但是,我无法运行 Pixels 示例,因此我首先要确保 Winit 可以正常运行。 从 GitHub 下载 Winit 存储库并运行示例可以正常工作。window

'window' example running in the Winit source repository

但是,如果我创建一个新项目并将示例代码复制粘贴到其中,那么运行代码将不再打开窗口。

[![Same example code running in my own project](https://i.stack.imgur.com/slLOh.png)](https://i.stack.imgur.com/slLOh.png)

运行 gdb 后,代码似乎卡住了,但我找不到太多其他东西。window.request_redraw()

我对窗口系统不是很了解,但从运行和我分别得到和,我相信这表明 WSL 同时安装了 X11 和 Wayland 功能。echo $DISPLAYecho $WAYLAND_DISPLAY:0wayland-0

我正在使用 .正在运行打印 。Ubuntu 22.04.3 LTScat /proc/versionLinux version 5.15.90.1-microsoft-standard-WSL2 (oe-user@oe-host) (x86_64-msft-linux-gcc (GCC) 9.3.0, GNU ld (GNU Binutils) 2.34.0.20200220) #1 SMP Fri Jan 27 02:56:13 UTC 2023

我似乎对 Cargo 如何管理依赖项有一些误解,因为我不知道为什么当我指示 Cargo 下载相同版本的 Winit 源代码时,相同的代码会在 Winit 源项目中运行,而不是在我自己的项目中运行。我尝试过 Winit v0.29、v0.28 和 v0.27,但同样的问题仍然存在。

重现步骤:

git clone https://github.com/rust-windowing/winit.git
cd winit
cargo run --example window

窗口打开正常...

cd ..
cargo new window
cd window
cargo add winit
cargo add simple_logger
cp ../winit/examples/window.rs src/main.rs
mkdir src/util
cp ../winit/examples/util/fill.rs src/util
cargo run

窗口打不开...

Rust Windows-subsystem-for-linux x11 wayland winit

评论

1赞 Chayim Friedman 11/1/2023
尝试将 和 从他们的 Cargo.toml 复制到您的 .[dependencies][dev-dependencies][dependencies]
2赞 cafce25 11/1/2023
请以格式化文本的形式提供错误文本,而不是图像!
0赞 Cosimos Cendo 11/2/2023
@cafce25,我很抱歉!

答:

1赞 Cosimos Cendo 11/2/2023 #1

解决!

TL;DR 示例代码有一个功能标志,我没有在自己的项目中启用。


在对 中的主要示例代码进行徒劳的调试后,我处理了 中的帮助程序代码。有一个函数有两个签名:window.rsfill.rsfill_window()

#[cfg(all(feature = "rwh_05", not(any(target_os = "android", target_os = "ios"))))]
pub(super) fn fill_window(window: &Window) {
    ...
}
    
#[cfg(not(all(feature = "rwh_05", not(any(target_os = "android", target_os = "ios")))))]
pub(super) fn fill_window(_window: &Window) {
    // No-op on mobile platforms.
}

第一个应在启用该功能时运行,但不是 或 。 否则,第二个应该运行。rwh_05target_osandroidios

我在每个函数中都放了一个,发现我的项目正在编译到第二个(无操作)函数,而源项目正在编译到第一个函数。println!()windowwinit

因此,要么 、 ,要么未启用。target_os == androidtarget_os == iosrwh_05

我通过将代码添加到fill.rs

#[cfg(target_os = "android")]
compile_error!("target_os = android");

#[cfg(target_os = "ios")]
compile_error!("target_os = android");

#[cfg(target_os = "linux")]
compile_error!("target_os = linux");

输出显示 是 。target_oslinux

error: target_os = linux
  --> src/util/fill.rs:16:1
   |
16 | compile_error!("target_os = linux");
   | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^

error: could not compile `window` (bin "window") due to previous error

下一个

#[cfg(feature = "rwh_05")]
compile_error!("rwh_05 feature enabled");

#[cfg(not(feature = "rwh_05"))]
compile_error!("rwh_05 feature is not enabled");

输出显示未启用⠀rwh_05

error: rwh_05 feature is not enabled
  --> src/util/fill.rs:16:1
   |
16 | compile_error!("rwh_05 feature is not enabled");
   | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^

error: could not compile `window` (bin "window") due to previous error

这就是我得到启示的地方。

我错误地认为它会全局启用,而实际上它只为板条箱启用了该功能,而不是我自己的本地项目。Cargo.tomlrwh_05winit

[dependencies]
winit = { path = "./winit", features = ["rwh_05"] }

添加

[features]
rwh_05 = []

to 和 running with 按预期运行窗口示例:Cargo.tomlcargo run --features rwh_05

enter image description here