Move workspace module into its own crate

This commit is contained in:
Antonio Scandurra 2021-10-05 13:45:19 +02:00
parent 2087c4731f
commit 499616d769
24 changed files with 1696 additions and 1584 deletions

15
Cargo.lock generated
View File

@ -6031,6 +6031,20 @@ dependencies = [
[[package]]
name = "workspace"
version = "0.1.0"
dependencies = [
"anyhow",
"buffer",
"client",
"editor",
"gpui",
"log",
"postage",
"project",
"serde_json 1.0.64",
"theme",
"tree-sitter",
"tree-sitter-rust",
]
[[package]]
name = "wyz"
@ -6122,6 +6136,7 @@ dependencies = [
"unindent",
"url",
"util",
"workspace",
]
[[package]]

View File

@ -4,14 +4,13 @@ version = "0.1.0"
edition = "2018"
[features]
test-support = []
test-support = ["rpc/test-support"]
[dependencies]
gpui = { path = "../gpui" }
util = { path = "../util" }
rpc = { path = "../rpc" }
sum_tree = { path = "../sum_tree" }
anyhow = "1.0.38"
async-recursion = "0.3"
async-tungstenite = { version = "0.14", features = ["async-tls"] }

View File

@ -11,7 +11,7 @@ use async_tungstenite::tungstenite::{
error::Error as WebsocketError,
http::{Request, StatusCode},
};
use gpui::{AsyncAppContext, Entity, ModelContext, Task};
use gpui::{action, AsyncAppContext, Entity, ModelContext, MutableAppContext, Task};
use lazy_static::lazy_static;
use parking_lot::RwLock;
use postage::{prelude::Stream, watch};
@ -28,7 +28,7 @@ use std::{
};
use surf::Url;
use thiserror::Error;
use util::ResultExt;
use util::{ResultExt, TryFutureExt};
pub use channel::*;
pub use rpc::*;
@ -42,6 +42,16 @@ lazy_static! {
.and_then(|s| if s.is_empty() { None } else { Some(s) });
}
action!(Authenticate);
pub fn init(rpc: Arc<Client>, cx: &mut MutableAppContext) {
cx.add_global_action(move |_: &Authenticate, cx| {
let rpc = rpc.clone();
cx.spawn(|cx| async move { rpc.authenticate_and_connect(&cx).log_err().await })
.detach();
});
}
pub struct Client {
peer: Arc<Peer>,
state: RwLock<ClientState>,

View File

@ -283,7 +283,7 @@ pub struct EditorSettings {
pub style: EditorStyle,
}
#[derive(Clone, Deserialize)]
#[derive(Clone, Deserialize, Default)]
pub struct EditorStyle {
pub text: TextStyle,
#[serde(default)]

View File

@ -18,7 +18,7 @@ pub struct Label {
highlight_indices: Vec<usize>,
}
#[derive(Clone, Debug, Deserialize)]
#[derive(Clone, Debug, Deserialize, Default)]
pub struct LabelStyle {
pub text: TextStyle,
pub highlight_text: Option<TextStyle>,

View File

@ -167,6 +167,32 @@ impl From<TextStyle> for HighlightStyle {
}
}
impl Default for TextStyle {
fn default() -> Self {
FONT_CACHE.with(|font_cache| {
let font_cache = font_cache.borrow();
let font_cache = font_cache
.as_ref()
.expect("TextStyle::default can only be called within a call to with_font_cache");
let font_family_name = Arc::from("Courier");
let font_family_id = font_cache.load_family(&[&font_family_name]).unwrap();
let font_id = font_cache
.select_font(font_family_id, &Default::default())
.unwrap();
Self {
color: Default::default(),
font_family_name,
font_family_id,
font_id,
font_size: 14.,
font_properties: Default::default(),
underline: Default::default(),
}
})
}
}
impl HighlightStyle {
fn from_json(json: HighlightStyleJson) -> Self {
let font_properties = properties_from_json(json.weight, json.italic);

View File

@ -985,7 +985,7 @@ mod tests {
fs::{FakeFs, Fs as _},
people_panel::JoinWorktree,
project::{ProjectPath, Worktree},
workspace::Workspace,
workspace::{Workspace, WorkspaceParams},
};
#[gpui::test]
@ -1102,13 +1102,9 @@ mod tests {
let mut server = TestServer::start().await;
let (client_a, _) = server.create_client(&mut cx_a, "user_a").await;
let (client_b, user_store_b) = server.create_client(&mut cx_b, "user_b").await;
let app_state_b = zed::AppState {
client: client_b,
user_store: user_store_b,
..Arc::try_unwrap(cx_b.update(zed::test::test_app_state))
.ok()
.unwrap()
};
let mut workspace_b_params = cx_b.update(WorkspaceParams::test);
workspace_b_params.client = client_b;
workspace_b_params.user_store = user_store_b;
cx_a.foreground().forbid_parking();
@ -1141,7 +1137,7 @@ mod tests {
.await
.unwrap();
let (window_b, workspace_b) = cx_b.add_window(|cx| Workspace::new(&app_state_b, cx));
let (window_b, workspace_b) = cx_b.add_window(|cx| Workspace::new(&workspace_b_params, cx));
cx_b.update(|cx| {
cx.dispatch_action(
window_b,

View File

@ -14,7 +14,7 @@ pub use theme_registry::*;
pub const DEFAULT_THEME_NAME: &'static str = "black";
#[derive(Deserialize)]
#[derive(Deserialize, Default)]
pub struct Theme {
#[serde(default)]
pub name: String,
@ -26,7 +26,7 @@ pub struct Theme {
pub editor: EditorStyle,
}
#[derive(Deserialize)]
#[derive(Deserialize, Default)]
pub struct Workspace {
pub background: Color,
pub titlebar: Titlebar,
@ -37,7 +37,7 @@ pub struct Workspace {
pub right_sidebar: Sidebar,
}
#[derive(Clone, Deserialize)]
#[derive(Clone, Deserialize, Default)]
pub struct Titlebar {
#[serde(flatten)]
pub container: ContainerStyle,
@ -49,14 +49,14 @@ pub struct Titlebar {
pub outdated_warning: ContainedText,
}
#[derive(Clone, Deserialize)]
#[derive(Clone, Deserialize, Default)]
pub struct OfflineIcon {
#[serde(flatten)]
pub container: ContainerStyle,
pub width: f32,
}
#[derive(Clone, Deserialize)]
#[derive(Clone, Deserialize, Default)]
pub struct Tab {
pub height: f32,
#[serde(flatten)]
@ -71,7 +71,7 @@ pub struct Tab {
pub icon_conflict: Color,
}
#[derive(Deserialize)]
#[derive(Deserialize, Default)]
pub struct Sidebar {
#[serde(flatten)]
pub container: ContainerStyle,
@ -81,14 +81,14 @@ pub struct Sidebar {
pub resize_handle: ContainerStyle,
}
#[derive(Deserialize)]
#[derive(Deserialize, Default)]
pub struct SidebarItem {
pub icon_color: Color,
pub icon_size: f32,
pub height: f32,
}
#[derive(Deserialize)]
#[derive(Deserialize, Default)]
pub struct ChatPanel {
#[serde(flatten)]
pub container: ContainerStyle,
@ -100,7 +100,7 @@ pub struct ChatPanel {
pub hovered_sign_in_prompt: TextStyle,
}
#[derive(Debug, Deserialize)]
#[derive(Debug, Deserialize, Default)]
pub struct ProjectPanel {
#[serde(flatten)]
pub container: ContainerStyle,
@ -110,7 +110,7 @@ pub struct ProjectPanel {
pub hovered_selected_entry: ProjectPanelEntry,
}
#[derive(Debug, Deserialize)]
#[derive(Debug, Deserialize, Default)]
pub struct ProjectPanelEntry {
pub height: f32,
#[serde(flatten)]
@ -121,7 +121,7 @@ pub struct ProjectPanelEntry {
pub icon_spacing: f32,
}
#[derive(Deserialize)]
#[derive(Deserialize, Default)]
pub struct PeoplePanel {
#[serde(flatten)]
pub container: ContainerStyle,
@ -136,7 +136,7 @@ pub struct PeoplePanel {
pub hovered_unshared_worktree: WorktreeRow,
}
#[derive(Deserialize)]
#[derive(Deserialize, Default)]
pub struct WorktreeRow {
#[serde(flatten)]
pub container: ContainerStyle,
@ -146,7 +146,7 @@ pub struct WorktreeRow {
pub guest_avatar_spacing: f32,
}
#[derive(Deserialize)]
#[derive(Deserialize, Default)]
pub struct ChatMessage {
#[serde(flatten)]
pub container: ContainerStyle,
@ -155,7 +155,7 @@ pub struct ChatMessage {
pub timestamp: ContainedText,
}
#[derive(Deserialize)]
#[derive(Deserialize, Default)]
pub struct ChannelSelect {
#[serde(flatten)]
pub container: ContainerStyle,
@ -167,7 +167,7 @@ pub struct ChannelSelect {
pub menu: ContainerStyle,
}
#[derive(Deserialize)]
#[derive(Deserialize, Default)]
pub struct ChannelName {
#[serde(flatten)]
pub container: ContainerStyle,
@ -175,7 +175,7 @@ pub struct ChannelName {
pub name: TextStyle,
}
#[derive(Deserialize)]
#[derive(Deserialize, Default)]
pub struct Selector {
#[serde(flatten)]
pub container: ContainerStyle,
@ -185,7 +185,7 @@ pub struct Selector {
pub active_item: ContainedLabel,
}
#[derive(Clone, Debug, Deserialize)]
#[derive(Clone, Debug, Deserialize, Default)]
pub struct ContainedText {
#[serde(flatten)]
pub container: ContainerStyle,
@ -193,7 +193,7 @@ pub struct ContainedText {
pub text: TextStyle,
}
#[derive(Deserialize)]
#[derive(Deserialize, Default)]
pub struct ContainedLabel {
#[serde(flatten)]
pub container: ContainerStyle,
@ -201,7 +201,7 @@ pub struct ContainedLabel {
pub label: LabelStyle,
}
#[derive(Clone, Deserialize)]
#[derive(Clone, Deserialize, Default)]
pub struct InputEditorStyle {
#[serde(flatten)]
pub container: ContainerStyle,

View File

@ -2,3 +2,31 @@
name = "workspace"
version = "0.1.0"
edition = "2018"
[features]
test-support = [
"client/test-support",
"project/test-support",
"tree-sitter",
"tree-sitter-rust"
]
[dependencies]
buffer = { path = "../buffer" }
client = { path = "../client" }
editor = { path = "../editor" }
gpui = { path = "../gpui" }
project = { path = "../project" }
theme = { path = "../theme" }
anyhow = "1.0.38"
log = "0.4"
postage = { version = "0.4.1", features = ["futures-traits"] }
tree-sitter = { version = "0.19.5", optional = true }
tree-sitter-rust = { version = "0.19.0", optional = true }
[dev-dependencies]
client = { path = "../client", features = ["test-support"] }
project = { path = "../project", features = ["test-support"] }
serde_json = { version = "1.0.64", features = ["preserve_order"] }
tree-sitter = "0.19.5"
tree-sitter-rust = "0.19.0"

View File

@ -1,11 +1,11 @@
use super::{Item, ItemView};
use crate::{project::ProjectPath, Settings};
use crate::Settings;
use anyhow::Result;
use buffer::{Buffer, File as _};
use editor::{Editor, EditorSettings, Event};
use gpui::{fonts::TextStyle, AppContext, ModelHandle, Task, ViewContext};
use postage::watch;
use project::Worktree;
use project::{ProjectPath, Worktree};
use std::path::Path;
impl Item for Buffer {

File diff suppressed because it is too large Load Diff

View File

@ -1,5 +1,5 @@
use super::{ItemViewHandle, SplitDirection};
use crate::{project::ProjectPath, settings::Settings};
use crate::Settings;
use gpui::{
action,
elements::*,
@ -9,6 +9,7 @@ use gpui::{
Entity, MutableAppContext, Quad, RenderContext, View, ViewContext, ViewHandle,
};
use postage::watch;
use project::ProjectPath;
use std::cmp;
action!(Split, SplitDirection);

View File

@ -36,6 +36,7 @@ rpc = { path = "../rpc" }
sum_tree = { path = "../sum_tree" }
theme = { path = "../theme" }
util = { path = "../util" }
workspace = { path = "../workspace" }
anyhow = "1.0.38"
async-recursion = "0.3"
async-trait = "0.1"
@ -83,6 +84,7 @@ project = { path = "../project", features = ["test-support"] }
rpc = { path = "../rpc", features = ["test-support"] }
client = { path = "../client", features = ["test-support"] }
util = { path = "../util", features = ["test-support"] }
workspace = { path = "../workspace", features = ["test-support"] }
cargo-bundle = "0.5.0"
env_logger = "0.8"
serde_json = { version = "1.0.64", features = ["preserve_order"] }

View File

@ -1,4 +1,3 @@
use crate::{settings::Settings, workspace::Workspace};
use editor::{Editor, EditorSettings};
use fuzzy::PathMatch;
use gpui::{
@ -23,6 +22,7 @@ use std::{
},
};
use util::post_inc;
use workspace::{Settings, Workspace};
pub struct FileFinder {
handle: WeakViewHandle<Self>,
@ -422,16 +422,15 @@ impl FileFinder {
#[cfg(test)]
mod tests {
use super::*;
use crate::{test::test_app_state, workspace::Workspace};
use editor::Insert;
use project::fs::FakeFs;
use serde_json::json;
use std::path::PathBuf;
use workspace::{Workspace, WorkspaceParams};
#[gpui::test]
async fn test_matching_paths(mut cx: gpui::TestAppContext) {
let app_state = cx.update(test_app_state);
app_state
let params = cx.update(WorkspaceParams::test);
params
.fs
.as_fake()
.insert_tree(
@ -449,7 +448,7 @@ mod tests {
editor::init(cx);
});
let (window_id, workspace) = cx.add_window(|cx| Workspace::new(&app_state, cx));
let (window_id, workspace) = cx.add_window(|cx| Workspace::new(&params, cx));
workspace
.update(&mut cx, |workspace, cx| {
workspace.add_worktree(Path::new("/root"), cx)
@ -493,7 +492,8 @@ mod tests {
#[gpui::test]
async fn test_matching_cancellation(mut cx: gpui::TestAppContext) {
let fs = Arc::new(FakeFs::new());
let params = cx.update(WorkspaceParams::test);
let fs = params.fs.as_fake();
fs.insert_tree(
"/dir",
json!({
@ -508,10 +508,7 @@ mod tests {
)
.await;
let mut app_state = cx.update(test_app_state);
Arc::get_mut(&mut app_state).unwrap().fs = fs;
let (_, workspace) = cx.add_window(|cx| Workspace::new(&app_state, cx));
let (_, workspace) = cx.add_window(|cx| Workspace::new(&params, cx));
workspace
.update(&mut cx, |workspace, cx| {
workspace.add_worktree("/dir".as_ref(), cx)
@ -522,7 +519,7 @@ mod tests {
.await;
let (_, finder) = cx.add_window(|cx| {
FileFinder::new(
app_state.settings.clone(),
params.settings.clone(),
workspace.read(cx).project().clone(),
cx,
)
@ -569,14 +566,14 @@ mod tests {
#[gpui::test]
async fn test_single_file_worktrees(mut cx: gpui::TestAppContext) {
let app_state = cx.update(test_app_state);
app_state
let params = cx.update(WorkspaceParams::test);
params
.fs
.as_fake()
.insert_tree("/root", json!({ "the-parent-dir": { "the-file": "" } }))
.await;
let (_, workspace) = cx.add_window(|cx| Workspace::new(&app_state, cx));
let (_, workspace) = cx.add_window(|cx| Workspace::new(&params, cx));
workspace
.update(&mut cx, |workspace, cx| {
workspace.add_worktree(Path::new("/root/the-parent-dir/the-file"), cx)
@ -587,7 +584,7 @@ mod tests {
.await;
let (_, finder) = cx.add_window(|cx| {
FileFinder::new(
app_state.settings.clone(),
params.settings.clone(),
workspace.read(cx).project().clone(),
cx,
)
@ -622,8 +619,8 @@ mod tests {
#[gpui::test(retries = 5)]
async fn test_multiple_matches_with_same_relative_path(mut cx: gpui::TestAppContext) {
let app_state = cx.update(test_app_state);
app_state
let params = cx.update(WorkspaceParams::test);
params
.fs
.as_fake()
.insert_tree(
@ -635,7 +632,7 @@ mod tests {
)
.await;
let (_, workspace) = cx.add_window(|cx| Workspace::new(&app_state, cx));
let (_, workspace) = cx.add_window(|cx| Workspace::new(&params, cx));
workspace
.update(&mut cx, |workspace, cx| {
@ -650,7 +647,7 @@ mod tests {
let (_, finder) = cx.add_window(|cx| {
FileFinder::new(
app_state.settings.clone(),
params.settings.clone(),
workspace.read(cx).project().clone(),
cx,
)

View File

@ -5,11 +5,9 @@ pub mod language;
pub mod menus;
pub mod people_panel;
pub mod project_panel;
pub mod settings;
#[cfg(any(test, feature = "test-support"))]
pub mod test;
pub mod theme_selector;
pub mod workspace;
pub use buffer;
use buffer::LanguageRegistry;
@ -28,18 +26,15 @@ use people_panel::PeoplePanel;
use postage::watch;
pub use project::{self, fs};
use project_panel::ProjectPanel;
pub use settings::Settings;
use std::{path::PathBuf, sync::Arc};
use theme::ThemeRegistry;
use util::TryFutureExt;
use crate::workspace::Workspace;
pub use workspace;
use workspace::{Settings, Workspace, WorkspaceParams};
action!(About);
action!(Open, Arc<AppState>);
action!(OpenPaths, OpenParams);
action!(Quit);
action!(Authenticate);
action!(AdjustBufferFontSize, f32);
const MIN_FONT_SIZE: f32 = 6.0;
@ -69,15 +64,6 @@ pub fn init(app_state: &Arc<AppState>, cx: &mut gpui::MutableAppContext) {
cx.add_global_action(open_new);
cx.add_global_action(quit);
cx.add_global_action({
let rpc = app_state.client.clone();
move |_: &Authenticate, cx| {
let rpc = rpc.clone();
cx.spawn(|cx| async move { rpc.authenticate_and_connect(&cx).log_err().await })
.detach();
}
});
cx.add_global_action({
let settings_tx = app_state.settings_tx.clone();
@ -135,8 +121,9 @@ fn open_paths(action: &OpenPaths, cx: &mut MutableAppContext) -> Task<()> {
log::info!("open new workspace");
// Add a new workspace if necessary
let app_state = &action.0.app_state;
let (_, workspace) = cx.add_window(window_options(), |cx| {
build_workspace(&action.0.app_state, cx)
build_workspace(&WorkspaceParams::from(app_state.as_ref()), cx)
});
workspace.update(cx, |workspace, cx| {
workspace.open_paths(&action.0.paths, cx)
@ -145,33 +132,31 @@ fn open_paths(action: &OpenPaths, cx: &mut MutableAppContext) -> Task<()> {
fn open_new(action: &workspace::OpenNew, cx: &mut MutableAppContext) {
cx.add_window(window_options(), |cx| {
let mut workspace = build_workspace(action.0.as_ref(), cx);
let mut workspace = build_workspace(&action.0, cx);
workspace.open_new_file(&action, cx);
workspace
});
}
fn build_workspace(app_state: &AppState, cx: &mut ViewContext<Workspace>) -> Workspace {
let mut workspace = Workspace::new(app_state, cx);
fn build_workspace(params: &WorkspaceParams, cx: &mut ViewContext<Workspace>) -> Workspace {
let mut workspace = Workspace::new(params, cx);
let project = workspace.project().clone();
workspace.left_sidebar_mut().add_item(
"icons/folder-tree-16.svg",
ProjectPanel::new(project, app_state.settings.clone(), cx).into(),
ProjectPanel::new(project, params.settings.clone(), cx).into(),
);
workspace.right_sidebar_mut().add_item(
"icons/user-16.svg",
cx.add_view(|cx| {
PeoplePanel::new(app_state.user_store.clone(), app_state.settings.clone(), cx)
})
.into(),
cx.add_view(|cx| PeoplePanel::new(params.user_store.clone(), params.settings.clone(), cx))
.into(),
);
workspace.right_sidebar_mut().add_item(
"icons/comment-16.svg",
cx.add_view(|cx| {
ChatPanel::new(
app_state.client.clone(),
app_state.channel_list.clone(),
app_state.settings.clone(),
params.client.clone(),
params.channel_list.clone(),
params.settings.clone(),
cx,
)
})
@ -193,13 +178,27 @@ fn quit(_: &Quit, cx: &mut gpui::MutableAppContext) {
cx.platform().quit();
}
impl<'a> From<&'a AppState> for WorkspaceParams {
fn from(state: &'a AppState) -> Self {
Self {
client: state.client.clone(),
fs: state.fs.clone(),
languages: state.languages.clone(),
settings: state.settings.clone(),
user_store: state.user_store.clone(),
channel_list: state.channel_list.clone(),
}
}
}
#[cfg(test)]
mod tests {
use super::*;
use crate::{test::test_app_state, workspace::ItemView};
use serde_json::json;
use test::test_app_state;
use theme::DEFAULT_THEME_NAME;
use util::test::temp_tree;
use workspace::ItemView;
#[gpui::test]
async fn test_open_paths_action(mut cx: gpui::TestAppContext) {
@ -270,7 +269,7 @@ mod tests {
async fn test_new_empty_workspace(mut cx: gpui::TestAppContext) {
let app_state = cx.update(test_app_state);
cx.update(|cx| init(&app_state, cx));
cx.dispatch_global_action(workspace::OpenNew(app_state.clone()));
cx.dispatch_global_action(workspace::OpenNew(app_state.as_ref().into()));
let window_id = *cx.window_ids().first().unwrap();
let workspace = cx.root_view::<Workspace>(window_id).unwrap();
let editor = workspace.update(&mut cx, |workspace, cx| {

View File

@ -8,6 +8,7 @@ use parking_lot::Mutex;
use simplelog::SimpleLogger;
use std::{fs, path::PathBuf, sync::Arc};
use theme::ThemeRegistry;
use workspace::{self, settings, OpenNew};
use zed::{
self,
assets::Assets,
@ -15,9 +16,7 @@ use zed::{
client::{http, ChannelList, UserStore},
editor, file_finder,
fs::RealFs,
language, menus, people_panel, project_panel, settings, theme_selector,
workspace::{self, OpenNew},
AppState, OpenParams, OpenPaths,
language, menus, people_panel, project_panel, theme_selector, AppState, OpenParams, OpenPaths,
};
fn main() {
@ -54,6 +53,7 @@ fn main() {
});
zed::init(&app_state, cx);
client::init(app_state.client.clone(), cx);
workspace::init(cx);
editor::init(cx);
file_finder::init(cx);
@ -70,7 +70,7 @@ fn main() {
let paths = collect_path_args();
if paths.is_empty() {
cx.dispatch_global_action(OpenNew(app_state));
cx.dispatch_global_action(OpenNew(app_state.as_ref().into()));
} else {
cx.dispatch_global_action(OpenPaths(OpenParams { paths, app_state }));
}

View File

@ -1,9 +1,18 @@
use crate::{workspace, AppState};
use crate::{AppState, WorkspaceParams};
use gpui::{Menu, MenuItem};
use std::sync::Arc;
#[cfg(target_os = "macos")]
pub fn menus(state: &Arc<AppState>) -> Vec<Menu<'static>> {
let workspace_params = WorkspaceParams {
client: state.client.clone(),
fs: state.fs.clone(),
languages: state.languages.clone(),
settings: state.settings.clone(),
user_store: state.user_store.clone(),
channel_list: state.channel_list.clone(),
};
vec![
Menu {
name: "Zed",
@ -27,7 +36,7 @@ pub fn menus(state: &Arc<AppState>) -> Vec<Menu<'static>> {
MenuItem::Action {
name: "New",
keystroke: Some("cmd-n"),
action: Box::new(workspace::OpenNew(state.clone())),
action: Box::new(workspace::OpenNew(workspace_params)),
},
MenuItem::Separator,
MenuItem::Action {

View File

@ -1,4 +1,3 @@
use crate::{workspace::Workspace, Settings};
use client::{Collaborator, UserStore};
use gpui::{
action,
@ -10,6 +9,7 @@ use gpui::{
};
use postage::watch;
use theme::Theme;
use workspace::{Settings, Workspace};
action!(JoinWorktree, u64);
action!(LeaveWorktree, u64);

View File

@ -648,7 +648,7 @@ mod tests {
.read_with(&cx, |t, _| t.as_local().unwrap().scan_complete())
.await;
let (_, workspace) = cx.add_window(|cx| Workspace::new(&app_state, cx));
let (_, workspace) = cx.add_window(|cx| Workspace::new(&app_state.as_ref().into(), cx));
let panel = workspace.update(&mut cx, |_, cx| ProjectPanel::new(project, settings, cx));
assert_eq!(
visible_entry_details(&panel, 0..50, &mut cx),

View File

@ -1,4 +1,4 @@
use crate::{assets::Assets, language, settings::Settings, AppState};
use crate::{assets::Assets, language, AppState};
use buffer::LanguageRegistry;
use client::{http::ServerResponse, test::FakeHttpClient, ChannelList, Client, UserStore};
use gpui::{AssetSource, MutableAppContext};
@ -7,6 +7,7 @@ use postage::watch;
use project::fs::FakeFs;
use std::sync::Arc;
use theme::{Theme, ThemeRegistry, DEFAULT_THEME_NAME};
use workspace::Settings;
#[cfg(test)]
#[ctor::ctor]

File diff suppressed because it is too large Load Diff