Contour Terminal Emulator - Internals
Repository Layout
docs/ - Contour documentation and website
cmake/ - CMake helper modules
scripts/ - general development assisting and CI helper scripts
src/ - Contour source code
contour/ - GUI terminal emulator application (business logic)
crispy/ - fundamentals library
text_shaper/ - font location and text shaping & rasterization library
vtbackend/ - core terminal library
vtparser/ - VT parser library
vtpty/ - PTY library
vtrasterizer/ - frontend independent Terminal rendering library
test/ - Contains a set of test scripts.
crispy
library
This library contains super generic helper functions that are too small to be their own library and ease general development.
text_shaper
library
This library abstracts font location service, text shaping, as well as glyph rasterization into a platform independent API.
vtpty
library
vtpty
provides an abstract API to construct a PTY handle
to communicate between a terminal emulator (master) and a connected application (slave).
vtparser
library
vtparser
library provides an API to parse VT sequences. This library
can be used on the master side (terminal emulator)
as well as slave side (terminal application, e.g. the shell).
vtbackend
library
Here we implement the actual terminal emulation. This is a headless library
and cannot just be used for a GUI terminal emulator software.
In order to render the screen state of a terminal to
pixels, the vtrasterizer
library can be used.
vtrasterizer
library
vtrasterizer
implements rasterizing the screen state into a bitmap.
This is done target independent, which means, that the caller must provide
the respective implementation to decide how the pixels are being stored (or rendered).
Process Threading Model
Contour Terminal Emulator is multithreaded. The main thread is solely for receiving user input events and displaying screen updates plus some necessary administrative tasks.
The slave application will be spawned as a process and a thread is being associated with it to exclusively read the application's output, which will be processed inside the same thread. That thread is responsible for updating the internal terminal state.
How terminal input is being processed
The user can send keyboard and mouse input
which the connected slave (application) will read
from its stdin
.
- The native OS will emit an event, which will be intercepted by GLFW3 (the OpenGL Framework)
- The target GUI input events are being mapped to
terminal
API input events (seeInputGenerator
) - The
terminal::InputEvent
objects are send to the respectiveterminal_view::TerminalView
, which will apply key binds, if applicable, or pass the events toterminal::Terminal
. - The
terminal::Terminal
instance will useterminal::InputGenerator
to generate VT sequences depending on current mode flags. - The generated VT sequences are being transmitted to the slave application.
How terminal output is being processed
The connected slave (application) may write a stream of characters to stdout
or stderr
,
which will be read by the terminal.
- The VT stream is being parsed by a VT
Parser
that emits raw events - These events are taken by the
OutputHandler
, and translated toCommand
variant types - in case of a VT function (such as ESC, CSI, OSC) a unique ID is being constructed. This unique ID is then mapped to aFunctionDef
with aFunctionHandler
whereas the latter will perform semantic analysis in order to emit the higher levelCommand
variant types. - The
Command
variant types are then processed in order by theScreen
instance, that ultimatively interprets them. - A callback hooks is being invoked to notify about screen updates (useful for displaying updated screen contents).