This commit is contained in:
Junkui Zhang 2025-08-25 21:28:50 +08:00
parent 98fc52f438
commit cb09b8f675
7 changed files with 60 additions and 51 deletions

View file

@ -2588,7 +2588,7 @@ impl Editor {
|| binding || binding
.keystrokes() .keystrokes()
.first() .first()
.is_some_and(|keystroke| keystroke.modifiers.modified()) .is_some_and(|keystroke| keystroke.display_modifiers.modified())
})) }))
} }
@ -7686,16 +7686,16 @@ impl Editor {
.keystroke() .keystroke()
{ {
modifiers_held = modifiers_held modifiers_held = modifiers_held
|| (&accept_keystroke.modifiers == modifiers || (&accept_keystroke.display_modifiers == modifiers
&& accept_keystroke.modifiers.modified()); && accept_keystroke.display_modifiers.modified());
}; };
if let Some(accept_partial_keystroke) = self if let Some(accept_partial_keystroke) = self
.accept_edit_prediction_keybind(true, window, cx) .accept_edit_prediction_keybind(true, window, cx)
.keystroke() .keystroke()
{ {
modifiers_held = modifiers_held modifiers_held = modifiers_held
|| (&accept_partial_keystroke.modifiers == modifiers || (&accept_partial_keystroke.display_modifiers == modifiers
&& accept_partial_keystroke.modifiers.modified()); && accept_partial_keystroke.display_modifiers.modified());
} }
if modifiers_held { if modifiers_held {
@ -9044,7 +9044,7 @@ impl Editor {
let is_platform_style_mac = PlatformStyle::platform() == PlatformStyle::Mac; let is_platform_style_mac = PlatformStyle::platform() == PlatformStyle::Mac;
let modifiers_color = if accept_keystroke.modifiers == window.modifiers() { let modifiers_color = if accept_keystroke.display_modifiers == window.modifiers() {
Color::Accent Color::Accent
} else { } else {
Color::Muted Color::Muted
@ -9056,19 +9056,19 @@ impl Editor {
.font(theme::ThemeSettings::get_global(cx).buffer_font.clone()) .font(theme::ThemeSettings::get_global(cx).buffer_font.clone())
.text_size(TextSize::XSmall.rems(cx)) .text_size(TextSize::XSmall.rems(cx))
.child(h_flex().children(ui::render_modifiers( .child(h_flex().children(ui::render_modifiers(
&accept_keystroke.modifiers, &accept_keystroke.display_modifiers,
PlatformStyle::platform(), PlatformStyle::platform(),
Some(modifiers_color), Some(modifiers_color),
Some(IconSize::XSmall.rems().into()), Some(IconSize::XSmall.rems().into()),
true, true,
))) )))
.when(is_platform_style_mac, |parent| { .when(is_platform_style_mac, |parent| {
parent.child(accept_keystroke.key.clone()) parent.child(accept_keystroke.display_key.clone())
}) })
.when(!is_platform_style_mac, |parent| { .when(!is_platform_style_mac, |parent| {
parent.child( parent.child(
Key::new( Key::new(
util::capitalize(&accept_keystroke.key), util::capitalize(&accept_keystroke.display_key),
Some(Color::Default), Some(Color::Default),
) )
.size(Some(IconSize::XSmall.rems().into())), .size(Some(IconSize::XSmall.rems().into())),
@ -9249,7 +9249,7 @@ impl Editor {
accept_keystroke.as_ref(), accept_keystroke.as_ref(),
|el, accept_keystroke| { |el, accept_keystroke| {
el.child(h_flex().children(ui::render_modifiers( el.child(h_flex().children(ui::render_modifiers(
&accept_keystroke.modifiers, &accept_keystroke.display_modifiers,
PlatformStyle::platform(), PlatformStyle::platform(),
Some(Color::Default), Some(Color::Default),
Some(IconSize::XSmall.rems().into()), Some(IconSize::XSmall.rems().into()),
@ -9319,7 +9319,7 @@ impl Editor {
.child(completion), .child(completion),
) )
.when_some(accept_keystroke, |el, accept_keystroke| { .when_some(accept_keystroke, |el, accept_keystroke| {
if !accept_keystroke.modifiers.modified() { if !accept_keystroke.display_modifiers.modified() {
return el; return el;
} }
@ -9338,7 +9338,7 @@ impl Editor {
.font(theme::ThemeSettings::get_global(cx).buffer_font.clone()) .font(theme::ThemeSettings::get_global(cx).buffer_font.clone())
.when(is_platform_style_mac, |parent| parent.gap_1()) .when(is_platform_style_mac, |parent| parent.gap_1())
.child(h_flex().children(ui::render_modifiers( .child(h_flex().children(ui::render_modifiers(
&accept_keystroke.modifiers, &accept_keystroke.display_modifiers,
PlatformStyle::platform(), PlatformStyle::platform(),
Some(if !has_completion { Some(if !has_completion {
Color::Muted Color::Muted

View file

@ -38,9 +38,9 @@ pub struct KeybindingKeystroke {
/// TODO: /// TODO:
pub inner: Keystroke, pub inner: Keystroke,
/// TODO: /// TODO:
pub modifiers: Modifiers, pub display_modifiers: Modifiers,
/// TODO: /// TODO:
pub key: String, pub display_key: String,
} }
/// Error type for `Keystroke::parse`. This is used instead of `anyhow::Error` so that Zed can use /// Error type for `Keystroke::parse`. This is used instead of `anyhow::Error` so that Zed can use
@ -300,8 +300,8 @@ impl KeybindingKeystroke {
let modifiers = keystroke.modifiers; let modifiers = keystroke.modifiers;
KeybindingKeystroke { KeybindingKeystroke {
inner: keystroke, inner: keystroke,
modifiers, display_modifiers: modifiers,
key, display_key: key,
} }
} }
} }
@ -369,8 +369,8 @@ impl std::fmt::Display for Keystroke {
impl std::fmt::Display for KeybindingKeystroke { impl std::fmt::Display for KeybindingKeystroke {
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result { fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
display_modifiers(&self.modifiers, f)?; display_modifiers(&self.display_modifiers, f)?;
display_key(&self.key, f) display_key(&self.display_key, f)
} }
} }

View file

@ -85,8 +85,8 @@ impl PlatformKeyboardMapper for WindowsKeyboardMapper {
KeybindingKeystroke { KeybindingKeystroke {
inner: keystroke, inner: keystroke,
modifiers, display_modifiers: modifiers,
key, display_key: key,
} }
} }
} }
@ -140,7 +140,7 @@ impl WindowsKeyboardMapper {
fn get_vkey_from_key(&self, key: &str, use_key_equivalents: bool) -> Option<(u16, bool)> { fn get_vkey_from_key(&self, key: &str, use_key_equivalents: bool) -> Option<(u16, bool)> {
if use_key_equivalents { if use_key_equivalents {
key_needs_processing(key) get_vkey_from_key_with_us_layout(key)
} else { } else {
self.key_to_vkey.get(key).cloned() self.key_to_vkey.get(key).cloned()
} }
@ -240,8 +240,9 @@ pub(crate) fn generate_key_char(
} }
} }
fn key_needs_processing(key: &str) -> Option<(u16, bool)> { fn get_vkey_from_key_with_us_layout(key: &str) -> Option<(u16, bool)> {
match key { match key {
// ` => VK_OEM_3
"`" => Some((VK_OEM_3.0, false)), "`" => Some((VK_OEM_3.0, false)),
"~" => Some((VK_OEM_3.0, true)), "~" => Some((VK_OEM_3.0, true)),
"1" => Some((VK_1.0, false)), "1" => Some((VK_1.0, false)),
@ -331,8 +332,8 @@ mod tests {
}; };
let mapped = mapper.map_key_equivalent(keystroke.clone(), true); let mapped = mapper.map_key_equivalent(keystroke.clone(), true);
assert_eq!(mapped.inner, keystroke); assert_eq!(mapped.inner, keystroke);
assert_eq!(mapped.key, "a"); assert_eq!(mapped.display_key, "a");
assert_eq!(mapped.modifiers, Modifiers::control()); assert_eq!(mapped.display_modifiers, Modifiers::control());
// Shifted case, ctrl-$ // Shifted case, ctrl-$
let keystroke = Keystroke { let keystroke = Keystroke {
@ -342,8 +343,8 @@ mod tests {
}; };
let mapped = mapper.map_key_equivalent(keystroke.clone(), true); let mapped = mapper.map_key_equivalent(keystroke.clone(), true);
assert_eq!(mapped.inner, keystroke); assert_eq!(mapped.inner, keystroke);
assert_eq!(mapped.key, "4"); assert_eq!(mapped.display_key, "4");
assert_eq!(mapped.modifiers, Modifiers::control_shift()); assert_eq!(mapped.display_modifiers, Modifiers::control_shift());
// Shifted case, but shift is true // Shifted case, but shift is true
let keystroke = Keystroke { let keystroke = Keystroke {
@ -353,8 +354,8 @@ mod tests {
}; };
let mapped = mapper.map_key_equivalent(keystroke, true); let mapped = mapper.map_key_equivalent(keystroke, true);
assert_eq!(mapped.inner.modifiers, Modifiers::control()); assert_eq!(mapped.inner.modifiers, Modifiers::control());
assert_eq!(mapped.key, "4"); assert_eq!(mapped.display_key, "4");
assert_eq!(mapped.modifiers, Modifiers::control_shift()); assert_eq!(mapped.display_modifiers, Modifiers::control_shift());
// Windows style // Windows style
let keystroke = Keystroke { let keystroke = Keystroke {
@ -365,7 +366,7 @@ mod tests {
let mapped = mapper.map_key_equivalent(keystroke, true); let mapped = mapper.map_key_equivalent(keystroke, true);
assert_eq!(mapped.inner.modifiers, Modifiers::control()); assert_eq!(mapped.inner.modifiers, Modifiers::control());
assert_eq!(mapped.inner.key, "$"); assert_eq!(mapped.inner.key, "$");
assert_eq!(mapped.key, "4"); assert_eq!(mapped.display_key, "4");
assert_eq!(mapped.modifiers, Modifiers::control_shift()); assert_eq!(mapped.display_modifiers, Modifiers::control_shift());
} }
} }

View file

@ -2452,8 +2452,8 @@ impl KeybindingEditorModal {
fn remove_key_char( fn remove_key_char(
KeybindingKeystroke { KeybindingKeystroke {
inner, inner,
modifiers, display_modifiers,
key, display_key,
}: KeybindingKeystroke, }: KeybindingKeystroke,
) -> KeybindingKeystroke { ) -> KeybindingKeystroke {
KeybindingKeystroke { KeybindingKeystroke {
@ -2462,8 +2462,8 @@ fn remove_key_char(
key: inner.key, key: inner.key,
key_char: None, key_char: None,
}, },
modifiers, display_modifiers,
key, display_key,
} }
} }

View file

@ -116,7 +116,7 @@ impl KeystrokeInput {
&& self && self
.keystrokes .keystrokes
.last() .last()
.is_some_and(|last| last.key.is_empty()) .is_some_and(|last| last.display_key.is_empty())
{ {
return &self.keystrokes[..self.keystrokes.len() - 1]; return &self.keystrokes[..self.keystrokes.len() - 1];
} }
@ -130,8 +130,8 @@ impl KeystrokeInput {
key: "".to_string(), key: "".to_string(),
key_char: None, key_char: None,
}, },
modifiers, display_modifiers: modifiers,
key: "".to_string(), display_key: "".to_string(),
} }
} }
@ -258,7 +258,7 @@ impl KeystrokeInput {
self.keystrokes_changed(cx); self.keystrokes_changed(cx);
if let Some(last) = self.keystrokes.last_mut() if let Some(last) = self.keystrokes.last_mut()
&& last.key.is_empty() && last.display_key.is_empty()
&& keystrokes_len <= Self::KEYSTROKE_COUNT_MAX && keystrokes_len <= Self::KEYSTROKE_COUNT_MAX
{ {
if !self.search && !event.modifiers.modified() { if !self.search && !event.modifiers.modified() {
@ -267,14 +267,14 @@ impl KeystrokeInput {
} }
if self.search { if self.search {
if self.previous_modifiers.modified() { if self.previous_modifiers.modified() {
last.modifiers |= event.modifiers; last.display_modifiers |= event.modifiers;
last.inner.modifiers |= event.modifiers; last.inner.modifiers |= event.modifiers;
} else { } else {
self.keystrokes.push(Self::dummy(event.modifiers)); self.keystrokes.push(Self::dummy(event.modifiers));
} }
self.previous_modifiers |= event.modifiers; self.previous_modifiers |= event.modifiers;
} else { } else {
last.modifiers = event.modifiers; last.display_modifiers = event.modifiers;
last.inner.modifiers = event.modifiers; last.inner.modifiers = event.modifiers;
return; return;
} }
@ -306,13 +306,13 @@ impl KeystrokeInput {
let mut keystroke = let mut keystroke =
KeybindingKeystroke::new(keystroke.clone(), false, cx.keyboard_mapper()); KeybindingKeystroke::new(keystroke.clone(), false, cx.keyboard_mapper());
if let Some(last) = self.keystrokes.last() if let Some(last) = self.keystrokes.last()
&& last.key.is_empty() && last.display_key.is_empty()
&& (!self.search || self.previous_modifiers.modified()) && (!self.search || self.previous_modifiers.modified())
{ {
let key = keystroke.key.clone(); let display_key = keystroke.display_key.clone();
let inner_key = keystroke.inner.key.clone(); let inner_key = keystroke.inner.key.clone();
keystroke = last.clone(); keystroke = last.clone();
keystroke.key = key; keystroke.display_key = display_key;
keystroke.inner.key = inner_key; keystroke.inner.key = inner_key;
self.keystrokes.pop(); self.keystrokes.pop();
} }
@ -333,11 +333,14 @@ impl KeystrokeInput {
self.keystrokes_changed(cx); self.keystrokes_changed(cx);
if self.search { if self.search {
self.previous_modifiers = keystroke.modifiers; self.previous_modifiers = keystroke.display_modifiers;
return; return;
} }
if self.keystrokes.len() < Self::KEYSTROKE_COUNT_MAX && keystroke.modifiers.modified() { if self.keystrokes.len() < Self::KEYSTROKE_COUNT_MAX
self.keystrokes.push(Self::dummy(keystroke.modifiers)); && keystroke.display_modifiers.modified()
{
self.keystrokes
.push(Self::dummy(keystroke.display_modifiers));
} }
} }

View file

@ -124,7 +124,7 @@ impl RenderOnce for KeyBinding {
"KEY_BINDING-{}", "KEY_BINDING-{}",
self.keystrokes self.keystrokes
.iter() .iter()
.map(|k| k.key.to_string()) .map(|k| k.display_key.to_string())
.collect::<Vec<_>>() .collect::<Vec<_>>()
.join(" ") .join(" ")
) )
@ -166,7 +166,7 @@ pub fn render_keybinding_keystroke(
let element = Key::new( let element = Key::new(
keystroke_text( keystroke_text(
&keystroke.modifiers, &keystroke.modifiers,
&keystroke.key, &keystroke.display_key,
platform_style, platform_style,
vim_mode, vim_mode,
), ),
@ -184,7 +184,12 @@ pub fn render_keybinding_keystroke(
size, size,
true, true,
)); ));
elements.push(render_key(&keystroke.key, color, platform_style, size)); elements.push(render_key(
&keystroke.display_key,
color,
platform_style,
size,
));
elements elements
} }
} }
@ -414,7 +419,7 @@ pub fn text_for_keybinding_keystrokes(keystrokes: &[KeybindingKeystroke], cx: &A
.map(|keystroke| { .map(|keystroke| {
keystroke_text( keystroke_text(
&keystroke.modifiers, &keystroke.modifiers,
&keystroke.key, &keystroke.display_key,
platform_style, platform_style,
vim_enabled, vim_enabled,
) )

View file

@ -4729,7 +4729,7 @@ mod tests {
// and key strokes contain the given key // and key strokes contain the given key
bindings bindings
.into_iter() .into_iter()
.any(|binding| binding.keystrokes().iter().any(|k| k.key == key)), .any(|binding| binding.keystrokes().iter().any(|k| k.display_key == key)),
"On {} Failed to find {} with key binding {}", "On {} Failed to find {} with key binding {}",
line, line,
action.name(), action.name(),