g_prefix.rs

 1use crate::{mode::Mode, SwitchMode, VimState};
 2use gpui::{actions, keymap::Binding, MutableAppContext, ViewContext};
 3use workspace::Workspace;
 4
 5actions!(vim, [MoveToStart]);
 6
 7pub fn init(cx: &mut MutableAppContext) {
 8    let context = Some("Editor && vim_mode == normal && vim_submode == g");
 9    cx.add_bindings(vec![
10        Binding::new("g", MoveToStart, context),
11        Binding::new("escape", SwitchMode(Mode::normal()), context),
12    ]);
13
14    cx.add_action(move_to_start);
15}
16
17fn move_to_start(_: &mut Workspace, _: &MoveToStart, cx: &mut ViewContext<Workspace>) {
18    VimState::update_global(cx, |state, cx| {
19        state.update_active_editor(cx, |editor, cx| {
20            editor.move_to_beginning(&editor::MoveToBeginning, cx);
21        });
22        state.switch_mode(&SwitchMode(Mode::normal()), cx);
23    })
24}
25
26#[cfg(test)]
27mod test {
28    use indoc::indoc;
29
30    use crate::{
31        mode::{Mode, NormalState},
32        vim_test_context::VimTestContext,
33    };
34
35    #[gpui::test]
36    async fn test_g_prefix_and_abort(cx: &mut gpui::TestAppContext) {
37        let mut cx = VimTestContext::new(cx, true, "").await;
38
39        // Can abort with escape to get back to normal mode
40        cx.simulate_keystroke("g");
41        assert_eq!(cx.mode(), Mode::Normal(NormalState::GPrefix));
42        cx.simulate_keystroke("escape");
43        assert_eq!(cx.mode(), Mode::normal());
44    }
45
46    #[gpui::test]
47    async fn test_move_to_start(cx: &mut gpui::TestAppContext) {
48        let initial_content = indoc! {"
49            The quick
50            
51            brown fox jumps
52            over the lazy dog"};
53        let mut cx = VimTestContext::new(cx, true, initial_content).await;
54
55        // Jump to the end to
56        cx.simulate_keystroke("shift-G");
57        cx.assert_editor_state(indoc! {"
58            The quick
59            
60            brown fox jumps
61            over the lazy do|g"});
62
63        // Jump to the start
64        cx.simulate_keystrokes(&["g", "g"]);
65        cx.assert_editor_state(indoc! {"
66            |The quick
67            
68            brown fox jumps
69            over the lazy dog"});
70        assert_eq!(cx.mode(), Mode::normal());
71
72        // Repeat action doesn't change
73        cx.simulate_keystrokes(&["g", "g"]);
74        cx.assert_editor_state(indoc! {"
75            |The quick
76            
77            brown fox jumps
78            over the lazy dog"});
79        assert_eq!(cx.mode(), Mode::normal());
80    }
81}