keymap_ui: Syntax highlight context (#33864)
Closes #ISSUE Uses Rust for syntax highlighting of context in the keymap editor. Future pass will improve color choice to make colors less abrasive Release Notes: - N/A *or* Added/Fixed/Improved ...
This commit is contained in:
parent
4e6b7ee3ea
commit
fcdd99e244
3 changed files with 50 additions and 8 deletions
1
Cargo.lock
generated
1
Cargo.lock
generated
|
@ -14590,6 +14590,7 @@ dependencies = [
|
||||||
"settings",
|
"settings",
|
||||||
"theme",
|
"theme",
|
||||||
"tree-sitter-json",
|
"tree-sitter-json",
|
||||||
|
"tree-sitter-rust",
|
||||||
"ui",
|
"ui",
|
||||||
"util",
|
"util",
|
||||||
"workspace",
|
"workspace",
|
||||||
|
|
|
@ -34,6 +34,7 @@ serde.workspace = true
|
||||||
settings.workspace = true
|
settings.workspace = true
|
||||||
theme.workspace = true
|
theme.workspace = true
|
||||||
tree-sitter-json.workspace = true
|
tree-sitter-json.workspace = true
|
||||||
|
tree-sitter-rust.workspace = true
|
||||||
ui.workspace = true
|
ui.workspace = true
|
||||||
util.workspace = true
|
util.workspace = true
|
||||||
workspace-hack.workspace = true
|
workspace-hack.workspace = true
|
||||||
|
|
|
@ -249,6 +249,7 @@ impl KeymapEditor {
|
||||||
|
|
||||||
fn process_bindings(
|
fn process_bindings(
|
||||||
json_language: Arc<Language>,
|
json_language: Arc<Language>,
|
||||||
|
rust_language: Arc<Language>,
|
||||||
cx: &mut App,
|
cx: &mut App,
|
||||||
) -> (Vec<ProcessedKeybinding>, Vec<StringMatchCandidate>) {
|
) -> (Vec<ProcessedKeybinding>, Vec<StringMatchCandidate>) {
|
||||||
let key_bindings_ptr = cx.key_bindings();
|
let key_bindings_ptr = cx.key_bindings();
|
||||||
|
@ -272,7 +273,9 @@ impl KeymapEditor {
|
||||||
|
|
||||||
let context = key_binding
|
let context = key_binding
|
||||||
.predicate()
|
.predicate()
|
||||||
.map(|predicate| KeybindContextString::Local(predicate.to_string().into()))
|
.map(|predicate| {
|
||||||
|
KeybindContextString::Local(predicate.to_string().into(), rust_language.clone())
|
||||||
|
})
|
||||||
.unwrap_or(KeybindContextString::Global);
|
.unwrap_or(KeybindContextString::Global);
|
||||||
|
|
||||||
let source = source.map(|source| (source, source.name().into()));
|
let source = source.map(|source| (source, source.name().into()));
|
||||||
|
@ -320,11 +323,12 @@ impl KeymapEditor {
|
||||||
fn update_keybindings(&mut self, cx: &mut Context<KeymapEditor>) {
|
fn update_keybindings(&mut self, cx: &mut Context<KeymapEditor>) {
|
||||||
let workspace = self.workspace.clone();
|
let workspace = self.workspace.clone();
|
||||||
cx.spawn(async move |this, cx| {
|
cx.spawn(async move |this, cx| {
|
||||||
let json_language = Self::load_json_language(workspace, cx).await;
|
let json_language = Self::load_json_language(workspace.clone(), cx).await;
|
||||||
|
let rust_language = Self::load_rust_language(workspace.clone(), cx).await;
|
||||||
|
|
||||||
let query = this.update(cx, |this, cx| {
|
let query = this.update(cx, |this, cx| {
|
||||||
let (key_bindings, string_match_candidates) =
|
let (key_bindings, string_match_candidates) =
|
||||||
Self::process_bindings(json_language.clone(), cx);
|
Self::process_bindings(json_language, rust_language, cx);
|
||||||
this.keybindings = key_bindings;
|
this.keybindings = key_bindings;
|
||||||
this.string_match_candidates = Arc::new(string_match_candidates);
|
this.string_match_candidates = Arc::new(string_match_candidates);
|
||||||
this.matches = this
|
this.matches = this
|
||||||
|
@ -375,6 +379,35 @@ impl KeymapEditor {
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
async fn load_rust_language(
|
||||||
|
workspace: WeakEntity<Workspace>,
|
||||||
|
cx: &mut AsyncApp,
|
||||||
|
) -> Arc<Language> {
|
||||||
|
let rust_language_task = workspace
|
||||||
|
.read_with(cx, |workspace, cx| {
|
||||||
|
workspace
|
||||||
|
.project()
|
||||||
|
.read(cx)
|
||||||
|
.languages()
|
||||||
|
.language_for_name("Rust")
|
||||||
|
})
|
||||||
|
.context("Failed to load Rust language")
|
||||||
|
.log_err();
|
||||||
|
let rust_language = match rust_language_task {
|
||||||
|
Some(task) => task.await.context("Failed to load Rust language").log_err(),
|
||||||
|
None => None,
|
||||||
|
};
|
||||||
|
return rust_language.unwrap_or_else(|| {
|
||||||
|
Arc::new(Language::new(
|
||||||
|
LanguageConfig {
|
||||||
|
name: "Rust".into(),
|
||||||
|
..Default::default()
|
||||||
|
},
|
||||||
|
Some(tree_sitter_rust::LANGUAGE.into()),
|
||||||
|
))
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
fn dispatch_context(&self, _window: &Window, _cx: &Context<Self>) -> KeyContext {
|
fn dispatch_context(&self, _window: &Window, _cx: &Context<Self>) -> KeyContext {
|
||||||
let mut dispatch_context = KeyContext::new_with_defaults();
|
let mut dispatch_context = KeyContext::new_with_defaults();
|
||||||
dispatch_context.add("KeymapEditor");
|
dispatch_context.add("KeymapEditor");
|
||||||
|
@ -550,7 +583,7 @@ struct ProcessedKeybinding {
|
||||||
#[derive(Clone, Debug, IntoElement)]
|
#[derive(Clone, Debug, IntoElement)]
|
||||||
enum KeybindContextString {
|
enum KeybindContextString {
|
||||||
Global,
|
Global,
|
||||||
Local(SharedString),
|
Local(SharedString, Arc<Language>),
|
||||||
}
|
}
|
||||||
|
|
||||||
impl KeybindContextString {
|
impl KeybindContextString {
|
||||||
|
@ -559,14 +592,14 @@ impl KeybindContextString {
|
||||||
pub fn local(&self) -> Option<&SharedString> {
|
pub fn local(&self) -> Option<&SharedString> {
|
||||||
match self {
|
match self {
|
||||||
KeybindContextString::Global => None,
|
KeybindContextString::Global => None,
|
||||||
KeybindContextString::Local(name) => Some(name),
|
KeybindContextString::Local(name, _) => Some(name),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn local_str(&self) -> Option<&str> {
|
pub fn local_str(&self) -> Option<&str> {
|
||||||
match self {
|
match self {
|
||||||
KeybindContextString::Global => None,
|
KeybindContextString::Global => None,
|
||||||
KeybindContextString::Local(name) => Some(name),
|
KeybindContextString::Local(name, _) => Some(name),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -574,8 +607,15 @@ impl KeybindContextString {
|
||||||
impl RenderOnce for KeybindContextString {
|
impl RenderOnce for KeybindContextString {
|
||||||
fn render(self, _window: &mut Window, _cx: &mut App) -> impl IntoElement {
|
fn render(self, _window: &mut Window, _cx: &mut App) -> impl IntoElement {
|
||||||
match self {
|
match self {
|
||||||
KeybindContextString::Global => KeybindContextString::GLOBAL.clone(),
|
KeybindContextString::Global => StyledText::new(KeybindContextString::GLOBAL.clone())
|
||||||
KeybindContextString::Local(name) => name,
|
.with_highlights([(
|
||||||
|
0..KeybindContextString::GLOBAL.len(),
|
||||||
|
gpui::HighlightStyle::color(_cx.theme().colors().text_muted),
|
||||||
|
)])
|
||||||
|
.into_any_element(),
|
||||||
|
KeybindContextString::Local(name, language) => {
|
||||||
|
SyntaxHighlightedText::new(name, language).into_any_element()
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue