Andolika Labs / Sulekha

1.0 alpha सुलेख · fair handwriting · Linux

The PDF viewer for people who write LaTeX and teach from it.

Sulekha is a small, stylus-first PDF viewer and annotator. It reloads your paper as LaTeX rebuilds it, follows every cross-reference, and turns a Beamer deck into a lecture: presenter view, speaker notes, ink that clears itself, and a recording you can publish as video.

Made for what LaTeX produces

Most viewers treat a PDF as a picture. Sulekha treats it as the output of a build: a file that changes, that points at itself, and that sometimes moves.

Rebuild, and it is already on screen

Reading mode never holds the file open. Run latexmk in one window and the page redraws in the other, on the page you were reading. No lock, no stale copy, no reopen.

  • Opens read-only by default. A file from the command line, a file manager or a browser is for reading. One key switches to annotating when you meant to write on it.
  • Dark reading inverts the display without touching the file, so a paper reads at night and prints the right way up.
  • Fast cold start, parallel rasterisation with prefetch, and anchored zoom that stays sharp at every scale.
# one terminal
latexmk -pvc -pdf paper.tex

# the other, once; it follows the file from then on
sulekha paper.pdf

# open a paper at the proof you are checking
sulekha --page 14 --find "Lemma 3" paper.pdf

Cross-references that show, not just jump

Rest the pointer on a \cite and the bibliography entry appears where you are. Rest on a \ref to a figure and you get the figure with its caption. Following the link is optional, which is most of the work of reading a paper with references in it.

  • The item itself, not a slice of the page: entries are found by their hanging indent, captions by their gap.
  • Click to turn to the target; URLs open in your browser. Only http, https and mailto are honoured, never javascript: or file:.
  • Contents sidebar from the document's outline, text selection and copy, and find with match navigation.

animate package

\animateinline and \animategraphics play at the rate the file asks for, looping or in palindrome, several to a slide, restarting each time you arrive. No JavaScript is run; Sulekha reads the frames and keeps the clock itself.

media9 video

\includemedia clips play inside the slide, on page open or on a click. The H.264 inside the PDF is pulled out and played directly, so it works years after Flash stopped.

Beamer overlays

Speaker notes accept a range, ## Slides 4-6, so one note covers every overlay of a logical slide. Chapter marks in an exported video follow the deck's table of contents.

Teach from your Beamer deck

Press F5, or start the lecture in one command. The deck goes fullscreen on the projector and the presenter view opens on your screen.

A presenter view that is a mirror

It shows the slide the room sees, the next one, the slide number, an elapsed timer and the time of day. Ink, laser and spotlight appear on it live, exactly as the audience sees them. And because that is where your hands are, drawing on the presenter view lands on the screen behind you.

  • Ink is ephemeral. Draw over a slide and it clears when you move on, so next year's deck does not carry this year's arrows. Press e to keep it.
  • Laser pointer and spotlight, blank to black or white, and the screen is held awake for the whole talk.
  • d swaps the displays when the compositor puts the deck on the laptop and the presenter view on the projector. Every lecture starts that way somewhere.
  • A pen is in hand the moment the talk begins. The eraser reaches stage ink too, from the stylus's other end or 5.
→ ← SpaceNext / previous slide, what a clicker sends
b / wBlank to black / white
l / sLaser pointer / spotlight
1–4 / 5Take up an instrument / the eraser
x / eWipe this slide's ink / keep ink instead of clearing
a / Shift+AHold animations / play them from the start
vStart or stop the video on this slide
t / Shift+RStart or pause the timer / reset it
dSwap the displays
rPause or resume the recording
Esc F5 qEnd the presentation

Speaker notes in Markdown, beside the deck

lec01.pdf gets lec01.notes.md, a heading per slide. It lives beside the PDF rather than inside it, because a deck is regenerated and anything written into it is lost on the next build. The file is re-read every time you save it, including mid-rehearsal with the presenter view open.

  • Maths renders. $\Delta t \le \frac{h^2}{2\alpha}$ comes out as symbols, fractions and roots. What it does not understand is shown as written, never swallowed.
  • Code is coloured for Python, C/C++/CUDA, Julia, MATLAB, Fortran, Rust, shell and TeX. Pipe tables line up.
  • The layout fits the screen. A full-height column on an ultrawide at the lectern, the band under a 16:9 deck on a 16:10 laptop, or a sidebar. Long notes set in two balanced columns, with type that grows with the pane.
  • Edit Speaker Notes… writes the template for you, with each slide's title from the outline, and never overwrites a file that exists.
## Slide 1
Welcome them. Names, office hours, and **why this course exists**.

## Slides 4-6
One note for the whole overlay build-up.

## Slide 12: Stability
Cost is $\mathcal{O}(N \log N)$, stability needs
$\Delta t \le \frac{h^2}{2\alpha}$. Say why before the proof.

```python
u = pad(u, 2)                    # two ghost cells
u[2:-2] += dt * laplacian(u, h)  # explicit
```

Record the lecture. Publish the video.

Your voice, the slide changes and every stroke of ink, with its own timing, so a line replays as it was drawn rather than appearing whole.

A recording you can read without Sulekha

The talk lands in a directory beside the deck: a plain-text timeline and a WAV file. The timeline is written as the talk happens, so a laptop that dies at minute fifty leaves fifty minutes behind. The audio has no encoder in the path, because an encoder is one more thing to fail an hour into a lecture.

  • Replay in place, navigating by slide rather than by minute. The sound is the clock, so an hour in, a stroke still lands on the sentence that explains it.
  • Pause for questions with r. The presenter view shows a red recording indicator and warns when no sound is arriving.
  • Animations and video are in the recording, at the moment the room saw them, with ink on top.
lec05.pdf
lec05.notes.md
lec05-20260929-1430.talk/
    talk.txt        the timeline, plain text
    audio.wav       the voice
lec05-20260929-1430.mp4              after export
lec05-20260929-1430.chapters.txt     for the description box
sulekha-talk 1
deck lec05.pdf
0      slide 1
14320  slide 2
19022  ink 2 pen ballpoint 2.5 e02020ff | 120.4,88.1,1,0 …
41880  clear 2
42110  blank black

Export to video, with a chapter per slide

One H.264 file beside the recording, 1920 pixels wide at the deck's aspect ratio by default. An hour of lecture encodes in about two minutes. Chapters are named from the deck's table of contents, so the slide where a section begins reads Slide 6, Truncation error and the slides under it are just numbered.

  • YouTube-ready chapter list written alongside as plain timestamps, ready to paste into a description.
  • Scriptable. Record, export and upload from a shell script with no window ever opening.
  • Only the export needs ffmpeg. Recording and replay work without it.
# start the lecture in one command
sulekha --present lec05.pdf

# present and record together
sulekha --record lec05.pdf

# watch the newest recording back
sulekha --replay lec05.pdf

# export it to video and quit, no window
sulekha --export-width 2560 lec05.pdf
# lec05-20260929-1430.chapters.txt
0:00 Slide 1 — Introduction
1:05 Slide 2
4:31 Slide 3 — Truncation error

And a serious annotator the rest of the week

Marking papers, grading, signing forms, keeping a notebook. The editing verbs are deliberately few: draw, highlight, erase, add page, delete page, reorder page. That restriction is the product.

Pressure-sensitive ink

Four nibs, a translucent highlighter that sits behind the text, a stroke eraser and one that rubs out part of a stroke. Low latency with retroactive palm rejection.

Four instruments

Each slot is a complete pen with its own kind, nib, width and colour, set from one popup and shown in its own colour on the palette.

Text-snap highlights

Select words and highlight them as real PDF highlight annotations. Every note and highlight is listed in the sidebar.

Shapes and lasso

Line, arrow, rectangle and ellipse with whatever pen is in hand. Loop ink to move or resize it.

Typed notes and forms

Tap and type a note saved as FreeText. Fill text fields, checkboxes, radios and menus, with the fillable parts washed pale blue so a form says it is one.

Signatures

Sign once, then tap to place from a library. Saving in place keeps an existing digital signature intact.

Pages

Insert, delete, reorder, rotate and extract a selection to a new file, from a thumbnail sidebar with drag-to-reorder.

Notebooks

New documents from paper templates: blank, ruled, grid, dotted or Cornell, with a coloured cover, in a library with folders.

Print with the ink on it

The paper turns to suit a landscape deck by itself, and the preview opens in Sulekha when the desktop has no previewer.

Never lose ink

Undo and redo, crash recovery that offers unsaved ink back, and a prompt before anything would discard it.

Everything is a PDF

A notebook is a PDF whose pages came from a template. No second format, no import or export step, no sidecar to lose. Ink is written as standard annotations that every other reader renders, with the raw pressure samples alongside so Sulekha can reopen a stroke losslessly instead of degrading it to a polyline.

Saving in place is incremental: the original bytes are untouched and only the changes are appended. A save costs what the edit cost, not what the document weighs.

/InkListThe centreline, so a basic viewer shows something sane
/AP /NThe exact variable-width outline a conforming viewer draws
/Sulekha_DataRaw pressure samples, for lossless re-editing
/BM /MultiplyHighlighters sit behind the text in every reader
/FreeText /HighlightTyped notes and text highlights, as any reader expects them

Get Sulekha

Free software under the AGPL-3.0. One small binary: Rust, GTK4 and libadwaita, with MuPDF underneath. Currently at 1.0 alpha and in daily use.

Arch Linux

A package built from the release tarball with the whole test suite run during the build. ffmpeg is optional, for video export only.

cd packaging && makepkg -f
sudo pacman -U sulekha-*.pkg.tar.zst

Flatpak

Builds against the GNOME 48 runtime with no network in the sandbox. The first build is slow because MuPDF is compiled from source.

flatpak-builder --user --install \
  --force-clean build \
  build-aux/org.andolika.Sulekha.yaml

From source

Needs Rust 1.85 or newer, GTK 4.16, libadwaita 1.6 and a C toolchain. Installs the binary, desktop entry, icon and AppStream metadata.

cargo build --release
make install          # into ~/.local
Platform Linux (Windows build under test) Licence AGPL-3.0-or-later Version 1.0.0-alpha.1 Source github.com/andolika/sulekha

Questions about Sulekha?

Teaching from a deck Sulekha trips over, or a paper it should handle better? Tell us. Bugs and decks that break things are especially welcome.