@@ -0,0 +1,128 @@
1+# fold
2+
3+One outline of notes and tasks, stored as plain Markdown, in the terminal.
4+
5+Everything you write — projects, notes, tasks, an inbox — is one tree. Headings and
6+bullets are its nodes; you read and edit any subtree on its own, move subtrees around,
7+and check tasks off. The files stay ordinary Markdown that `rg`, your editor and your
8+phone can read, and they sync with Syncthing.
9+
10+```
11+ fold › Homelab › NAS ⌕ Filter + Capture ↶ Undo ↷ Redo ☰ Commands ? Help
12+╭ Outline ───────────────────────╮╭ ZFS layout ▤ ─────────────────────────── ✎ Edit ─ ⋯ ─╮
13+│▾ Homelab 2/4 ││ # ZFS layout │
14+│ ▾ NAS 1/2 ││ ⚑ since 2024-03 │
15+│ ▾ ZFS layout ▤ 1/2 ⋯││ │
16+│ ▾ ☐ Snapshot policy ││ Mirrored pairs, no raidz. Snapshots hourly. │
17+│ ▸ Networking 1/2 ││ ## ☐ Snapshot policy │
18+│▾ Inbox ││ - hourly, keep 24 │
19+╰────────────────────────────────╯╰───────────────────────────────────────────────────────╯
20+```
21+
22+## Run it
23+
24+With Nix:
25+
26+```sh
27+nix run github:iko-soy/fold # the TUI on your vault
28+nix run github:iko-soy/fold -- --keys vim
29+```
30+
31+With Cargo (a recent stable Rust, and a C compiler for the syntax-highlighting grammars):
32+
33+```sh
34+cargo install --path crates/fold-cli
35+fold
36+```
37+
38+The vault is `--vault PATH`, else `$FOLD_VAULT`, else the nearest directory above the
39+current one that contains `root.md`, else `~/fold`. Pointed at an empty directory, the TUI
40+starts a new vault with an `# Inbox`.
41+
42+## Using it
43+
44+The TUI is mouse-first, and every action also has a key.
45+
46+- **Click** a row to select it; the reading pane on the right shows it. Click `▸`/`▾` to
47+ fold, `☐` to check a task off, a breadcrumb in the top bar to zoom out.
48+- **Double-click** a row to zoom into it. Double-click a line of text to edit it there.
49+- **Right-click** a row (or click its `⋯`) for everything you can do to a node: edit, new
50+ sibling or child, done, properties, move, indent, make a block, copy, paste, delete.
51+- **Drag** a row onto another row's title to nest it there, or to the left of a title to
52+ put it just before.
53+- **Filter** (`/`) finds nodes by title and text; **Commands** (`:`) lists every action by
54+ name; **Capture** (`c`) drops a note into today's inbox.
55+
56+Keys, in the outline: `j`/`k` move, `h`/`l` fold, `Enter` zooms, `e` edits, `x` checks a
57+task, `n`/`N` add a sibling or child, `J`/`K` move a node, `>`/`<` indent, `r` moves a
58+subtree elsewhere, `u`/`U` undo and redo, `?` shows everything. Everything is saved as you
59+go; `q` quits.
60+
61+### The editor
62+
63+`e` edits the selected subtree's Markdown in the reading pane. It saves on its own — when
64+you pause, when you leave a part of the tree that lives in another file, and when you're
65+done. Pick a keymap with `--keys` or `$FOLD_KEYS`, or click `⌨` in the editor's border:
66+
67+- **normal** (default) — a conventional editor like micro: Shift+arrows select,
68+ `Ctrl-C`/`X`/`V`, `Ctrl-Z`/`Y`, `Ctrl-S`, `Ctrl-F`.
69+- **vim** — modes, counts, motions, operators, text objects, `.`, `/`, `:w`/`:q`.
70+- **helix** — selection first: `w`/`x` select, `d`/`c`/`y` act on the selection.
71+
72+Long lines wrap (`zw` toggles), fenced code is syntax-highlighted in about 140 languages,
73+and pasting from the terminal and copying to the system clipboard both work.
74+
75+## The files
76+
77+A vault is a directory with `root.md` and, optionally, one file per **block**:
78+
79+```markdown
80+# Homelab
81+
82+Two boxes in the closet, one at Hetzner.
83+
84+## NAS
85+
86+### ![[dozzod-binwes-talsun-worbec]]
87+
88+## Networking
89+
90+- [ ] Replace the flaky switch
91+![[racfer-hattes-mislup-nodrys]]
92+```
93+
94+- A heading or a bullet is a node; nesting is the tree. Headings can sit under bullets,
95+ and levels go past six.
96+- A checkbox after the marker makes any node a task: `- [ ]`, `## [x]`.
97+- A node that gets a property (a due date, say) becomes a **block**: its own file,
98+ `racfer~order-new-switch.md`, with YAML frontmatter and an `id`, stitched into its parent
99+ by `![[id]]`. That's how a single task gets a due date, and how the inbox becomes a small
100+ file you can append to from a phone.
101+
102+Nothing else is special. Deleting goes to a trash (`$XDG_STATE_HOME/fold/trash`), and
103+Syncthing conflict copies are merged node by node, with anything that differs kept as a
104+`conflict:` block to resolve in the app.
105+
106+## The command line
107+
108+```sh
109+fold # the TUI
110+fold capture "call the plumber" # append to today's inbox (stdin if no text)
111+fold capture --task --to Homelab/NAS "check the scrub"
112+fold check [--fix] # diagnostics; --fix rewrites in canonical form
113+fold merge [--dry-run] # fold Syncthing conflict files in
114+fold trash list | fold trash restore ID
115+fold help
116+```
117+
118+## Developing
119+
120+```sh
121+nix develop # cargo, rustc, clippy, rustfmt, rust-analyzer
122+cargo test --workspace
123+nix flake check # the same tests, in the Nix sandbox
124+```
125+
126+The code is three crates: `fold-core` (parsing, rendering, the operations, merge),
127+`fold-tui` (the ratatui app) and `fold-cli` (the `fold` binary). [SPEC.md](SPEC.md) is the
128+design: the data model, the file format, every operation and the laws they keep.