cover_image

使用Rust Tauri创建一个启动栏应用程序

李明 coding到灯火阑珊
2023年08月20日 22:01

在这篇文章中我们使用Rust Tauri来构建一个类似的“启动栏”类型的应用程序。

搭建一个基本的Tauri应用程序

我们将使用tauri和create-tauri-app工具来快速搭建项目。使用cargo安装create-tauri-app,并使用以下命令选项运行它:
cargo install create-tauri-app

> cargo create-tauri-app

✔ Project name · tauri-launch
✔ Choose your package manager · cargo
✔ Choose your UI template · vanilla

运行后,应该在当前目录中看到一个新文件夹tauri-launch,这就是我们的项目目录。

为了确保一切都正确设置,应该能够在项目目录中运行以下命令。
cargo tauri dev
你会看到下面这些:

图片


启用我们需要的模块

Tauri包含大量可以为应用程序提供更多功能的特性。对于启动栏类型的应用程序,我们需要启用全局快捷方式,顾名思义,它将允许我们为窗口分配全局快捷方式。

在你的src-tauri/Cargo.toml文件中,修改tauri依赖项,现在应该是这样的:
tauri = {
    version = "1.2",
    features = ["shell-open""global-shortcut"]
}


从快捷方式启动

启用快捷方式后,我们需要添加一些代码来注册快捷方式并在调用时显示/隐藏窗口。

首先,我们将修改src-tauri/tauri.config.json文件,给我们的窗口一个标签,我们可以用它来获取窗口的句柄。

在文件的底部,你会发现一个windows列表。修改这里的窗口项,添加label项。可以使用任何字母数字字符串,在这种情况下,我们将其称为“launcher”。
"windows": [
    {
    "label""launcher",
    ... // 其他窗口选项
    }
]
接下来,我们将修改src-tauri/src/main.rs文件,以便它注册快捷方式并显示/隐藏我们的窗口。
// 我们想要注册为快捷键的组合键
const SHORTCUT: &str = "Ctrl+f";

fn register_shortcut(app: &mut App) -> Result<(), tauri::Error>  {
    let app_handle = app.app_handle();
    let mut shortcuts = app_handle.global_shortcut_manager();
    
    if !shortcuts.is_registered(SHORTCUT)? {
        shortcuts.register(
            SHORTCUT,
            move || toggle_launchbar(&app_handle)
        )?;
    }

    Ok(())
}

// 这应该与你的“tauri.config.json”中的“label”匹配。
const WINDOW: &str = "launcher";

fn toggle_launchbar(app: &AppHandle) {
    // Grab a handle to the window
    let window = app.get_window(WINDOW)
        .expect("Did you label your window?");

    // 检查当前是否可见,如果可见则隐藏。
    if let Ok(true) = window.is_visible() {
        let _ = window.hide();
    } else {
        let _ = window.show();
    }
}

fn main() {
    tauri::Builder::default()
        .invoke_handler(tauri::generate_handler![greet])
        .setup(move |app: &mut App| {
            if let Err(err) = register_shortcut(app) {
                eprintln!("Unable to register shortcut: {err}");
            }

            Ok(())
        })
        .run(tauri::generate_context!())
        .expect("error while running tauri application");
}

现在运行应用程序。一旦窗口弹出,尝试我们在代码中分配的Ctrl+f快捷键。你应该能够在显示或隐藏主窗口。

这是一个很好的开始,但是这个窗口太大了,对我们光滑的启动条来说太笨重了。


窗口美学

首先,回到src-tauri/tauri.config.json中的窗口设置,调整所创建窗口的高度和宽度。
"windows": [
    {
    "label""launcher",
    "height"128,
    "width"640,
    ... 
    }
]

在我们的例子中,我们将高度调整为128,宽度调整为640,当然你也可以调整为在屏幕上觉得舒服的大小。

图片

调整尺寸后,我们的窗户有点皱了。让我们做一点抛光,给我们的启动栏一个漂亮的新外观,首先,我们把窗户上的装饰品拿掉。如果你花了一些时间研究窗口配置的文档,将注意到几个有用的选项,即透明、装饰、中心和可见。

  • 将transparent设置为true将允许窗口具有透明度。

  • 将decorations设置为false将关闭窗口边框和标题栏。

  • 将center设置为true将在启动时自动将窗口居中。

  • 将visible设置为false将在启动时自动隐藏窗口。

将这些添加到窗口配置中并运行应用程序,看看会发生什么。你可以随意使用其他窗口配置选项,看看它们是如何影响窗口的。

如果你熟悉Spotlight或其他启动栏类型的应用程序,我们将需要圆角化并添加一些透明度。让我们进入HTML和CSS来调整启动栏的外观。


修改外观

在src/index.html文件中,我选择删除除文本输入之外的所有内容。
<body>
    <input type="text" id="launcher" />
</body>

并更新CSS,使页面符合我们为窗口配置设置的尺寸。输入框也被最大化,以填充整个空间,并有一个漂亮的边界半径,使启动条有圆角。CSS的重要部分如下所示:
html, body {
  margin: 0;
  padding: 0;
  width: 640px;
  height: 128px;
}

input {
  border-radius: 8px;
  border: 1px solid #000;
  box-sizing: border-box;

  font-size: 4em;
  outline: none;
  padding: 0 0.4em;

  height: 100%;
  width: 100%;
}

// 根据用户偏好更改配色方案
@media (prefers-color-scheme: dark) {
  input {
    color: #ffffff;
    background-color: #0f0f0fdd;
  }
}

@media (prefers-color-scheme: light) {
  input {
    color: #0f0f0f;
    background-color: #ffffffdd;
  }
}

通过cargo tauri dev运行应用程序,你应该会看到如下内容:

图片


探测提交

我们需要更新Javascript和Rust代码,以便从窗口探测到提交,并将输入框文本发送回Rust端以满足我们的处理需求。

需要调整了create-tauri-app生成的javascript代码,以侦听输入框中的按键,并且只在接收到Enter键时调用tauri命令。
const { invoke } = window.__TAURI__.tauri;

let inputEl;

async function greet() {
  // 将输入发送到Rust端
  await invoke("greet", { name: inputEl.value });
  // 重置输入框
  inputEl.value = "";
}

window.addEventListener("DOMContentLoaded", () => {
  inputEl = document.getElementById("launcher");
  // 添加一个keyup监听器并等待按下“Enter”
  inputEl.addEventListener(
    "keyup",
    (event) => {
      if (event.key === "Enter") {
        greet();
      }
    });
});

现在实现了客户端,我们可以调整Rust代码,这样我们就可以将结果输出到stdout中,并在完成时隐藏窗口。
#[tauri::command]
fn greet(window: tauri::Window, name: &str) {
    println!("Input received: {}", name);
    toggle_launchbar(&window.app_handle());
}



Rust · 目录
上一篇实现了Rust Trait的类型,那么该类型的引用也实现了trait吗?下一篇在Rust中使用Hyper和Tokio构建高性能HTTP代理服务器(基于路由)
继续滑动看下一个
coding到灯火阑珊
向上滑动看下一个