diff --git a/yazi-config/preset/keymap.toml b/yazi-config/preset/keymap.toml index c4d4d6b5..1efc59b3 100644 --- a/yazi-config/preset/keymap.toml +++ b/yazi-config/preset/keymap.toml @@ -82,7 +82,7 @@ keymap = [ { on = [ "S" ], run = "search rg", desc = "Search files by content using ripgrep" }, { on = [ "" ], run = "search none", desc = "Cancel the ongoing search" }, { on = [ "z" ], run = "plugin zoxide", desc = "Jump to a directory using zoxide" }, - { on = [ "Z" ], run = "jump fzf", desc = "Jump to a directory, or reveal a file using fzf" }, + { on = [ "Z" ], run = "plugin fzf", desc = "Jump to a directory, or reveal a file using fzf" }, # Linemode { on = [ "m", "s" ], run = "linemode size", desc = "Set linemode to size" }, diff --git a/yazi-config/preset/yazi.toml b/yazi-config/preset/yazi.toml index 0bb4b76e..852e1626 100644 --- a/yazi-config/preset/yazi.toml +++ b/yazi-config/preset/yazi.toml @@ -7,7 +7,7 @@ ratio = [ 1, 4, 3 ] sort_by = "alphabetical" sort_sensitive = false sort_reverse = false -sort_dir_first = false +sort_dir_first = true linemode = "none" show_hidden = false show_symlink = true diff --git a/yazi-core/src/tab/commands/jump.rs b/yazi-core/src/tab/commands/jump.rs index ccbae89b..47bd0976 100644 --- a/yazi-core/src/tab/commands/jump.rs +++ b/yazi-core/src/tab/commands/jump.rs @@ -1,8 +1,7 @@ use std::time::Duration; -use yazi_plugin::external::{self, FzfOpt}; -use yazi_proxy::{options::{NotifyLevel, NotifyOpt}, AppProxy, TabProxy, HIDER}; -use yazi_shared::{emit, event::Cmd, fs::ends_with_slash, Defer, Layer}; +use yazi_proxy::{options::{NotifyLevel, NotifyOpt}, AppProxy}; +use yazi_shared::{emit, event::Cmd, Layer}; use crate::tab::Tab; @@ -30,48 +29,27 @@ impl From for Opt { } impl Tab { + // TODO: Remove this once Yazi v0.2.7 is released pub fn jump(&self, opt: impl Into) { - let opt = opt.into() as Opt; - if opt.type_ == OptType::None { - return; - } - - // TODO: Remove this once Yazi v0.2.7 is released - if opt.type_ == OptType::Zoxide { - AppProxy::notify(NotifyOpt { + AppProxy::notify(NotifyOpt { title: "Jump".to_owned(), - content: r#"The `jump zoxide` command has been deprecated in Yazi v0.2.5. Please replace it with `plugin zoxide` in your `keymap.toml`. + content: r#"The `jump` command has been deprecated in Yazi v0.2.5. +Please replace `jump fzf` with `plugin fzf`, and `jump zoxide` with `plugin zoxide`, in your `keymap.toml`. See https://github.com/sxyazi/yazi/issues/865 for more details."#.to_owned(), level: NotifyLevel::Warn, timeout: Duration::from_secs(15), }); - emit!(Call(Cmd::args("plugin", vec!["zoxide".to_owned()]), Layer::App)); + let opt = opt.into() as Opt; + if opt.type_ == OptType::None { return; } - let cwd = self.current.cwd.clone(); - tokio::spawn(async move { - let _permit = HIDER.acquire().await.unwrap(); - let _defer = Defer::new(AppProxy::resume); - AppProxy::stop().await; - - let result = if opt.type_ == OptType::Fzf { - external::fzf(FzfOpt { cwd }).await - } else { - unreachable!() - }; - - let Ok(url) = result else { - return; - }; - - if opt.type_ == OptType::Fzf && !ends_with_slash(&url) { - TabProxy::reveal(&url) - } else { - TabProxy::cd(&url) - } - }); + if opt.type_ == OptType::Fzf { + emit!(Call(Cmd::args("plugin", vec!["fzf".to_owned()]), Layer::App)); + } else { + emit!(Call(Cmd::args("plugin", vec!["zoxide".to_owned()]), Layer::App)); + } } } diff --git a/yazi-plugin/preset/plugins/fzf.lua b/yazi-plugin/preset/plugins/fzf.lua new file mode 100644 index 00000000..faa54907 --- /dev/null +++ b/yazi-plugin/preset/plugins/fzf.lua @@ -0,0 +1,25 @@ +local cwd = ya.sync(function() return tostring(cx.active.current.cwd) end) + +local function notify(s, ...) ya.notify { title = "Fzf", content = string.format(s, ...), timeout = 5, level = "error" } end + +local function entry() + local _permit = ya.hide() + local cwd = cwd() + + local child, err = + Command("fzf"):cwd(cwd):stdin(Command.INHERIT):stdout(Command.PIPED):stderr(Command.INHERIT):spawn() + + if not child then + return notify("Spawn `fzf` failed with error code %s. Do you have it installed?", err) + end + + local output, err = child:wait_with_output() + if not output then + return notify("`fzf` exited with error code %s", err) + end + + local target = output.stdout:gsub("\n$", "") + ya.manager_emit(target:match("[/\\]$") and "cd" or "reveal", { target }) +end + +return { entry = entry } diff --git a/yazi-plugin/src/external/fzf.rs b/yazi-plugin/src/external/fzf.rs deleted file mode 100644 index dabfe8c5..00000000 --- a/yazi-plugin/src/external/fzf.rs +++ /dev/null @@ -1,22 +0,0 @@ -use std::{path::Path, process::Stdio}; - -use anyhow::{bail, Result}; -use tokio::process::Command; -use yazi_shared::fs::Url; - -pub struct FzfOpt { - pub cwd: Url, -} - -pub async fn fzf(opt: FzfOpt) -> Result { - let child = - Command::new("fzf").current_dir(&opt.cwd).kill_on_drop(true).stdout(Stdio::piped()).spawn()?; - - let output = child.wait_with_output().await?; - let selected = String::from_utf8_lossy(&output.stdout).trim().to_string(); - - if selected.is_empty() { - bail!("No match") - } - return Ok(Url::from(Path::new(&opt.cwd).join(selected))); -} diff --git a/yazi-plugin/src/external/mod.rs b/yazi-plugin/src/external/mod.rs index 42041c66..04bb43d8 100644 --- a/yazi-plugin/src/external/mod.rs +++ b/yazi-plugin/src/external/mod.rs @@ -1,11 +1,9 @@ mod fd; -mod fzf; mod highlighter; mod lsar; mod rg; pub use fd::*; -pub use fzf::*; pub use highlighter::*; pub use lsar::*; pub use rg::*; diff --git a/yazi-plugin/src/loader/loader.rs b/yazi-plugin/src/loader/loader.rs index 728fdb43..4893a8eb 100644 --- a/yazi-plugin/src/loader/loader.rs +++ b/yazi-plugin/src/loader/loader.rs @@ -29,6 +29,7 @@ impl Loader { "code" => include_bytes!("../../preset/plugins/code.lua"), "file" => include_bytes!("../../preset/plugins/file.lua"), "folder" => include_bytes!("../../preset/plugins/folder.lua"), + "fzf" => include_bytes!("../../preset/plugins/fzf.lua"), "image" => include_bytes!("../../preset/plugins/image.lua"), "json" => include_bytes!("../../preset/plugins/json.lua"), "mime" => include_bytes!("../../preset/plugins/mime.lua"),