Add delete, open file, and rename actions to the project panel

Co-authored-by: Julia <julia@zed.dev>
Co-authored-by: Marshall <marshall@zed.dev>
This commit is contained in:
Max Brunsfeld 2023-11-13 11:38:47 -08:00
parent 1968becf94
commit c0f34e3302

View file

@ -8,11 +8,11 @@ use file_associations::FileAssociations;
use anyhow::{anyhow, Result}; use anyhow::{anyhow, Result};
use gpui::{ use gpui::{
actions, div, px, rems, svg, uniform_list, Action, AppContext, AssetSource, AsyncAppContext, actions, div, px, rems, svg, uniform_list, Action, AppContext, AssetSource, AsyncWindowContext,
AsyncWindowContext, ClipboardItem, Component, Div, Element, Entity, EventEmitter, FocusEnabled, ClipboardItem, Component, Div, Entity, EventEmitter, FocusEnabled, FocusHandle, Model,
FocusHandle, Model, ParentElement as _, Pixels, Point, PromptLevel, Render, ParentElement as _, Pixels, Point, PromptLevel, Render, StatefulInteractive,
StatefulInteractive, StatefulInteractivity, StatelessInteractive, Styled, Task, StatefulInteractivity, StatelessInteractive, Styled, Task, UniformListScrollHandle, View,
UniformListScrollHandle, View, ViewContext, VisualContext as _, WeakView, WindowContext, ViewContext, VisualContext as _, WeakView, WindowContext,
}; };
use menu::{Confirm, SelectNext, SelectPrev}; use menu::{Confirm, SelectNext, SelectPrev};
use project::{ use project::{
@ -33,7 +33,7 @@ use std::{
use theme::ActiveTheme as _; use theme::ActiveTheme as _;
use ui::{h_stack, v_stack, Label}; use ui::{h_stack, v_stack, Label};
use unicase::UniCase; use unicase::UniCase;
use util::TryFutureExt; use util::{maybe, TryFutureExt};
use workspace::{ use workspace::{
dock::{DockPosition, PanelEvent}, dock::{DockPosition, PanelEvent},
Workspace, Workspace,
@ -131,12 +131,6 @@ pub fn init_settings(cx: &mut AppContext) {
pub fn init(assets: impl AssetSource, cx: &mut AppContext) { pub fn init(assets: impl AssetSource, cx: &mut AppContext) {
init_settings(cx); init_settings(cx);
file_associations::init(assets, cx); file_associations::init(assets, cx);
// cx.add_action(
// |this: &mut ProjectPanel, action: &Paste, cx: &mut ViewContext<ProjectPanel>| {
// this.paste(action, cx);
// },
// );
} }
#[derive(Debug)] #[derive(Debug)]
@ -560,22 +554,18 @@ impl ProjectPanel {
} }
} }
fn confirm(&mut self, _: &Confirm, cx: &mut ViewContext<Self>) -> Option<Task<Result<()>>> { fn confirm(&mut self, _: &Confirm, cx: &mut ViewContext<Self>) {
if let Some(task) = self.confirm_edit(cx) { if let Some(task) = self.confirm_edit(cx) {
return Some(task); task.detach_and_log_err(cx);
}
} }
None fn open_file(&mut self, _: &Open, cx: &mut ViewContext<Self>) {
}
fn open_file(&mut self, _: &Open, cx: &mut ViewContext<Self>) -> Option<Task<Result<()>>> {
if let Some((_, entry)) = self.selected_entry(cx) { if let Some((_, entry)) = self.selected_entry(cx) {
if entry.is_file() { if entry.is_file() {
self.open_entry(entry.id, true, cx); self.open_entry(entry.id, true, cx);
} }
} }
None
} }
fn confirm_edit(&mut self, cx: &mut ViewContext<Self>) -> Option<Task<Result<()>>> { fn confirm_edit(&mut self, cx: &mut ViewContext<Self>) -> Option<Task<Result<()>>> {
@ -781,17 +771,19 @@ impl ProjectPanel {
} }
} }
fn delete(&mut self, _: &Delete, cx: &mut ViewContext<Self>) -> Option<Task<Result<()>>> { fn delete(&mut self, _: &Delete, cx: &mut ViewContext<Self>) {
maybe!({
let Selection { entry_id, .. } = self.selection?; let Selection { entry_id, .. } = self.selection?;
let path = self.project.read(cx).path_for_entry(entry_id, cx)?.path; let path = self.project.read(cx).path_for_entry(entry_id, cx)?.path;
let file_name = path.file_name()?; let file_name = path.file_name()?;
let mut answer = cx.prompt( let answer = cx.prompt(
PromptLevel::Info, PromptLevel::Info,
&format!("Delete {file_name:?}?"), &format!("Delete {file_name:?}?"),
&["Delete", "Cancel"], &["Delete", "Cancel"],
); );
Some(cx.spawn(|this, mut cx| async move {
cx.spawn(|this, mut cx| async move {
if answer.await != Ok(0) { if answer.await != Ok(0) {
return Ok(()); return Ok(());
} }
@ -801,7 +793,10 @@ impl ProjectPanel {
.ok_or_else(|| anyhow!("no such entry")) .ok_or_else(|| anyhow!("no such entry"))
})?? })??
.await .await
})) })
.detach_and_log_err(cx);
Some(())
});
} }
fn select_next(&mut self, _: &SelectNext, cx: &mut ViewContext<Self>) { fn select_next(&mut self, _: &SelectNext, cx: &mut ViewContext<Self>) {
@ -878,8 +873,9 @@ impl ProjectPanel {
} }
} }
fn paste(&mut self, _: &Paste, cx: &mut ViewContext<Self>) -> Option<()> { fn paste(&mut self, _: &Paste, cx: &mut ViewContext<Self>) {
if let Some((worktree, entry)) = self.selected_entry(cx) { maybe!({
let (worktree, entry) = self.selected_entry(cx)?;
let clipboard_entry = self.clipboard_entry?; let clipboard_entry = self.clipboard_entry?;
if clipboard_entry.worktree_id() != worktree.id() { if clipboard_entry.worktree_id() != worktree.id() {
return None; return None;
@ -923,15 +919,16 @@ impl ProjectPanel {
if let Some(task) = self.project.update(cx, |project, cx| { if let Some(task) = self.project.update(cx, |project, cx| {
project.rename_entry(clipboard_entry.entry_id(), new_path, cx) project.rename_entry(clipboard_entry.entry_id(), new_path, cx)
}) { }) {
task.detach_and_log_err(cx) task.detach_and_log_err(cx);
} }
} else if let Some(task) = self.project.update(cx, |project, cx| { } else if let Some(task) = self.project.update(cx, |project, cx| {
project.copy_entry(clipboard_entry.entry_id(), new_path, cx) project.copy_entry(clipboard_entry.entry_id(), new_path, cx)
}) { }) {
task.detach_and_log_err(cx) task.detach_and_log_err(cx);
} }
}
None Some(())
});
} }
fn copy_path(&mut self, _: &CopyPath, cx: &mut ViewContext<Self>) { fn copy_path(&mut self, _: &CopyPath, cx: &mut ViewContext<Self>) {
@ -1368,7 +1365,7 @@ impl ProjectPanel {
}) })
.child( .child(
if let (Some(editor), true) = (editor, show_editor) { if let (Some(editor), true) = (editor, show_editor) {
div().child(editor.clone()) div().w_full().child(editor.clone())
} else { } else {
div().child(Label::new(details.filename.clone())) div().child(Label::new(details.filename.clone()))
} }
@ -1455,14 +1452,15 @@ impl Render for ProjectPanel {
.on_action(Self::new_file) .on_action(Self::new_file)
.on_action(Self::new_directory) .on_action(Self::new_directory)
.on_action(Self::rename) .on_action(Self::rename)
// .on_action(Self::delete) .on_action(Self::delete)
// .on_action(Self::confirm) .on_action(Self::confirm)
// .on_action(Self::open_file) .on_action(Self::open_file)
.on_action(Self::cancel) .on_action(Self::cancel)
.on_action(Self::cut) .on_action(Self::cut)
.on_action(Self::copy) .on_action(Self::copy)
.on_action(Self::copy_path) .on_action(Self::copy_path)
.on_action(Self::copy_relative_path) .on_action(Self::copy_relative_path)
.on_action(Self::paste)
.on_action(Self::reveal_in_finder) .on_action(Self::reveal_in_finder)
.on_action(Self::open_in_terminal) .on_action(Self::open_in_terminal)
.on_action(Self::new_search_in_directory) .on_action(Self::new_search_in_directory)