PARDES TUTOR tmux + vi + acme, from scratch. The model is acme's: EVERYTHING is text, editable and executable the same way. Modal editing (helix-style) lives on top of that. Press j until you reach the introduction. ================================================================= = INTRODUCTION = ================================================================= Pardes is tmux + vi + acme, made from scratch. The foundation is the acme model: a pane is just text on screen. There is no separate "buffer" type — what you see is what you edit. Some panes happen to be live terminals (tty mode); most are text you can move a cursor over. Modal editing (helix-style) is layered on top of that. Three modes (the tag shows which): nm NORMAL block cursor, keys move/edit. DEFAULT on startup. in INSERT keys type text at the cursor. sy TTY keys go straight to the shell. (terminals only) This tutor is in THREE parts, ordered by what's most different from editors you may know: PART 1 — the MOUSE. Acme's chording; nothing like Vim/Helix. PART 2 — the TTY. A terminal is just a pane; Enter positions you. PART 3 — the KEYS. Helix-style modal (with the Pardes differences). PRACTICE BLOCKS (part 3): the "# keys:" line lists keystrokes (space-separated; esc/enter/bs are special, the rest type each char). The clean lines under "# before" are what you practice on; the lines under "# after" are what you should end up with. "# at: row,col" (right after # keys:) sets where the cursor starts. These blocks are also run as unit tests (generated from this file by tutor_gen). Hold j to reach part 1. ================================================================= = PART 1 — THE MOUSE (acme chording; the most different part) = ================================================================= Acme's central idea: the THREE mouse buttons are a chording language over text. Pardes inherits this directly. (Vim and Helix have almost none of this — their mouse is for selection/scroll only.) LEFT (button 1) select text; a no-drag click also FOCUSES the pane and PINS the modal cursor where you click (so you can then edit there with the keyboard). MIDDLE (button 2) "execute" the selected text. Selecting a builtin name runs it; anything else is SENT to the shell the pane runs (if any). This is how you run a command you typed in text mode. RIGHT (button 3) "look" — resolve the word under the cursor as a path and open it: a directory opens/focuses a terminal there and ls's it; a file opens a file pane scrolled to a ":line" suffix if present. CHORDING (the acme magic): hold one button, press another. The classic is select-then-execute: - drag with LEFT to select a shell command you've typed - while STILL holding LEFT, press MIDDLE -> it runs - release both You can also select with LEFT then press RIGHT to "look" the selected word up as a file. Two-button chords = select-and-act in one gesture. THE TAG: every pane has a top bar (the "tag") — the pane's directory followed by the builtin command names (Newcol Delcol Del Tutor). It's just text: middle-click "Del" to close the window, "Newcol" to make a new column, "Delcol" to close the column, "Tutor" to spawn this tutor. Right-click a directory in any body to open a terminal there. LAYOUT: columns split horizontally, windows stack in each column. - drag the VERTICAL gap between columns to resize - drag the HORIZONTAL gap between stacked windows to resize - drag the red box (top-left of a pane) to MOVE a window between columns / reorder it - the scrollbar is the gutter below the box: left-click scrolls UP to that point, right-click scrolls DOWN (Mouse actions are hard to unit-test from text; they're covered by the e2e suite: middle-click execute, right-click dir/file open, tag builtins, drag-rearrange. See tests.zig steps 6-8.) ================================================================= = PART 2 — THE TTY (a terminal is just a pane) = ================================================================= This is the headline difference from Vim/Helix: there is no "open a terminal in a split" that's separate from "edit a file in a split". A TERMINAL IS A PANE. The same modal keys that edit a file navigate the terminal's screen, and dropping into tty REUSES the shell's own prompt model rather than layering an editor cursor on top. On a terminal pane: NORMAL (nm) shows the REAL shell — prompts and typed input visible. You navigate the screen with the same h/j/k/l/w/b/e as a file pane. INSERT (in) hides the prompt rows — a clean compose surface (acme-style) where you type a command to run. TTY (sy) keys go straight to the shell as terminal input. ESC: insert -> normal. (Never reaches tty.) ENTER: normal -> tty, AND moves the shell's REAL cursor to where your modal cursor was on the input line: - empty input -> shell cursor at the prompt START - typed text -> shell cursor at/after the char you navigated to (start-vs-end matters) This is tty-native: it reuses the shell's OSC 133 semantic prompt via ghostty's promptClickMove (our shell rc opts in with cl=line). The shell moves its own cursor with arrow keys it understands — Pardes doesn't fake a cursor on top. So the flow is: navigate the shell screen in normal, hit Enter exactly where you want to keep typing/editing, and you're IN the shell at that spot. No separate "terminal mode cursor" to reconcile. (Positioning needs a live shell + a pty; covered by the e2e suite, tests.zig step 4b: type ABCDEF, navigate to the F, Enter, type X -> ABCDEXF, proving the shell cursor moved mid-input.) ================================================================= = PART 3 — THE KEYS (helix-style modal, Pardes differences) = ================================================================= Same core as Helix and Vim: a block cursor you move with h/j/k/l, motions w/b/e, and you enter insert with i/a/o. The differences: - NO select mode / multi-cursor (Helix). Selection is LINE-first: `x` grows a line selection downward; d/c/y act on it. - NO verb+noun (Vim's dw, cw). Motions only MOVE. To delete a word you select its lines with x then d. - ESC never reaches tty. Enter does (on terminals). - Editing a file pane MUTATES real content; a terminal pane yanks rendered text and pastes it as an insertion run (shell output can't be deleted, only pasted text can). PRACTICE: run the keys on the "# before" lines; you should get the "# after" lines. (These blocks are unit tests too.) ----------------------------------------------------------------- = 3.1 MOVING THE CURSOR (h j k l) = ----------------------------------------------------------------- k * h = left, l = right h l * j = down, k = up (also: arrow keys) j The cursor sits ON a character (block). Motions only move. # keys: l l l # before abcdef # after abcdef ----------------------------------------------------------------- = 3.2 ENTERING INSERT: i a A I o O = ----------------------------------------------------------------- `i` insert at cursor. `a` insert AFTER the cursor. `A` insert at end of line. `I` insert at first non-blank. `o` open line BELOW + insert. `O` open line ABOVE + insert. (All match Vim and Helix.) # keys: i X esc # before bcdef # after Xbcdef Cursor on 'b' (col 0). `i` inserts before 'b'. # keys: a Z esc # before abc # after aZbc Cursor on 'a' (col 0). `a` inserts after 'a'. # keys: A Z esc # before abc # after abcZ `A` jumps to end then inserts — appends 'Z'. # keys: I Z esc # before abc # after Zabc `I` goes to the first non-blank ('a'), inserts before it. # keys: o line2 esc # before line1 # after line1 line2 `o` makes a blank line below, enters insert, "line2" typed, Esc. # keys: O top esc # before bot # after top bot ----------------------------------------------------------------- = 3.3 WORD MOTIONS: w b e (W B E long) = ----------------------------------------------------------------- `w` next word start, `b` prev word start, `e` next word END. W/B/E treat punctuation as part of the word. Same as Vim & Helix. # keys: w i Z esc # before foo bar # after foo Zbar `w` from 'f'(col0) lands on 'b'(col4). Insert before 'b'. # keys: e i Z esc # before foo bar # after foZo bar `e` from 'f' lands on 'o'(col2, end of "foo"). Insert before it. # keys: b i Z esc # at: 0,4 # before foo bar # after Zfoo bar Cursor on 'b'(col4, "bar"). `b` -> start of previous word = 'f'(col0). ----------------------------------------------------------------- = 3.4 LINE BOUNDS: 0 $ ^ g g G = ----------------------------------------------------------------- `0` start of line, `$` end, `^` first non-blank. `gg` first line, `G` last line. Same as Vim/Helix. # keys: $ i Z esc # before abcde # after abcdZe `$` to last char 'e', insert before it. (Cursor ON a char, so "end" = last char, not past it.) # keys: 0 i Z esc # before abcde # after Zabcde # keys: ^ i Z esc # before abcde # after Zabcde ----------------------------------------------------------------- = 3.5 LINE SELECTION + EDIT: x d c y p = ----------------------------------------------------------------- The Pardes difference. No `v` select-mode: `x` grows a line selection downward; d/c/y act on it. `x` start/extend a line selection `d` delete the selected lines (yanked) `c` clear the line + insert (change) `y` yank the selection (or current line) `p` paste the yank as a new line below # keys: x d # at: 1,0 # before keep gone # after keep Cursor on "gone" (row 1). `x` selects it, `d` deletes it. # keys: x x d # at: 1,0 # before a b c # after a `x` selects "b", `x` extends to "c", `d` removes both. # keys: x y j p # before orig dupe # after orig dupe orig `x` selects "orig", `y` yanks it, `j` to "dupe", `p` pastes below. # keys: x c typed esc # before old # after typed `x` selects "old", `c` clears it to an empty line + insert, type. # keys: c Q esc # at: 0,1 # before ab # after aQ No selection: cursor on 'b'(col1). `c` deletes 'b' + insert; type 'Q'. ----------------------------------------------------------------- = 3.6 VIEWPORT + PANES = ----------------------------------------------------------------- zt / zz / zb scroll so the cursor is at top/center/bottom Ctrl-d / Ctrl-u half-page down / up Ctrl-f / Ctrl-b full page down / up Ctrl-w h/j/k/l focus the pane left/down/up/right Alt-n new terminal below the active one Alt-c move the active terminal into a fresh column (No practice blocks: these are viewport/layout, not text edits.) ================================================================= = SUMMARY = ================================================================= MOUSE (acme): L select/focus+pin M execute R look(open) chord L+M = select-and-run; tag builtins (Del, ...) TTY: terminal IS a pane; Enter from normal -> tty AT the cursor's spot (start if empty, mid-text otherwise) KEYS (helix): h j k l w b e 0 $ ^ gg G x d c y p i a I A o O zt zz zb Ctrl-d/u/f/b Ctrl-w hjkl Alt-n/c vs Helix: no select-mode, no multi-cursor; selection is LINE-first. vs Vim: no verb+noun (dw); motions only move; Esc never reaches tty. vs both: a terminal is just a pane; the same keys edit text and navigate the shell screen, and Enter reuses the shell's own prompt to position you precisely. To spawn THIS tutor again from anywhere: middle-click "Tutor" in any pane's tag (it's a builtin, next to Newcol/Delcol/Del). Quit the tutor: this is a file pane — `:q` isn't wired; close the window (middle-click "Del" in the tag) or Ctrl-c the app.