ctx is a protocol/library/platform/terminal
for 2D vector graphics. Supporting the drawing vocabulary of
cairo/canvas. Interactive applications written with it can be used
transparently over serial communication (like ssh) as well as directly
on /dev/fb0 or /dev/dri/card0.
Features and references
- HTML5 Canvas 2D Context
- Easily bindable C API and protocol builds directly on this standard.
Compositing and blending is according to Compositing and Blending
Level 2; ctx goes further than the standard and permits all blending modes
to be combined with all compositing modes.
- Small footprint
- Can be tuned for microcontrollers down to ~7kb of RAM + 30kb
of code + 12kb of fontdata, combined with immediate mode UI that can
be re-run, it is sufficient to have a framebuffer covering one
or a few scanlines. More RAM permits more flexible arrangement
of more components using the CTX protocol.
- Threaded/deferred rendering
- The compact ctx protocol - in both text and binary form is a serialization of HTML5 Canvas 2D context API with
Thes drawlist representations are used for larger than RAM
framebuffers on microcontrollers, multi threaded SDL2 and /dev/fb0
rendering and network transparent rendering inside ctx terminal. When
used for graphical clients inside terminals; ctx is even applying
inter-frame compression; building the current frames drawlist out of
fragments of the preceding (reference) frames drawlist.
- utf8 native
- Ligature handling is missing, and beyond
vttest charset support is not good and RTL is missing -
harfbuzz intergration can fix this and more. Also currently
lacking color emoji. The most efficient font format is the
binary representation of the ctx protocol.
- VT4xx, ECMA-48
- Almost full vt100 and vt220 escape sequence handling, scrollback, bracketed paste, 256 and 24bit colors are supported - as well as a growing subset of vt400 and other relevant terminal escape sequences.
- ametameric palette
- The terminal 16 color palette is optimized for legibility for both trichromats and dichromats
- DEC terminal family standard for raster graphics transfer
- kitty graphics
- kitty style raster graphics transfer
- iterm2 inline images
- iterm2 style raster grarphics transfer
- Both ctx as a terminal/platform and
applications built with the ctx library can run
directly on the linux framebuffer without X/wayland, for it to be
fast a fast framebuffer is needed.
- RGB and CMYK, 8pc and 32bit floating point
supporting RGB332, 565 and grayscale modes with generic code
that also will handle more components than CMYKA - the
protocol/API has provisions for colorspaces but proper conversions are
not done yet.
- audio recording and playback (only raw pcm for now, opus codec NYI)
- If the declarations for stb_truetype are
included before ctx.h - functions to load fonts from TTF/OTF files
- Optional backend that works better than the framebuffer that gets included when SDL.h is included before ctx.h
- support code to render to cairo contexts if cairo.h is included before ctx.h, useful for conformance verfication and SVG and PDF output.
Development of ctx happens in a mono-repo, which contains a split up source-tree for the rasterizer/protocol that ends up in the single-header ctx.h files, a tool to generate ctx format subsetted fonts from TTF/OTF files, the sources for a client/terminal multi-plexer - as well as demo applications for the platform.
$ git clone https://ctx.graphics/.git
$ cd ctx.graphics
There is no tarball releases yet, but the development version
can be cloned and contains some example/test clients in C and bash,
if you've got the development headers for SDL2 the following
builds a ctx binary.
|ctx.h||760K||The singleheader library ctx.|
|ctx-font-regular.h||128K||Example font to use with ctx, to be a true single header solution - the ascii subset of this is included by default.|
|ctx-x86_64-static||64bit static linux binary - should work in mant distros, but has only DRM, /dev/fb0 and braille rendering not SDL2|
|ctx-i486-static||32bit static linux binary - should work in mant distros, but has only DRM, /dev/fb0 and braille rendering not SDL2|
license and funding
The terminal is available under GPLv3+, and
ctx.h is available under LGPLv3+ you
can encourage continued development of ctx and dissimilar technologies by
financially supporting me, Øyvind Kolås who is doing independent pro-bono R&D through
similar. If my income through such sources is above 4000USD per
month for a year, or a similar amount in shorter time the
protocol and rasterizer parts of ctx will be relicensed under
the ISC license.
The current status of ctx is beyond proof of concept - but
still does not fully realize a minimal system demonstrating
it's capabilities - some features are also broken and need
repair - and for third party use probably more urgently
than the following wishlist. When this list is nearing 0
it is time for a tarball release of ctx - event if the
single header ctx.h already is the rolling release.
- clip does not clip event boxes/shapes
- clip is not well behaved across save/restore - doing a clip of a 0,0,0x0 rectangle is currently recognized as "reset clip",
and can be used in front of the ctx_restore, which will become a no-op
when clipping is properly implemented
- arc not well behaved for edge-cases around full-circle
- in_fill is using bounding box - and most reliably works with rectangles.
- radial gradient is only using one center
- dimensions of drop-shadow are not transformed
- miter limit (unless round joins are used, all corners are mitered now)
- dash pattern for stroking is missing
- cursor keys incorrect (not passing vttest) in vt52 mode
- some form of built in palm supression is needed in drm/fbdev backend
some potential improvements
- improved performance
- code refactoring
- glyph fallbacks
- analytical instead of raster clipping
- texture upload as part of terminal protocol
- terminal rewrap on resize
- swap uses of cairo in GEGL with ctx
- ICC color management (provisions have been made in the API for this,
but RGBtoRGB and CMYKtoRGB RGBtoCMYK conversions are currently
done naively, instead of using babl.)
- websockets + js + HTML5 Canvas renderer/client for protocols
- wayland/libinput support
- (optional) use of floating point instead of fixed point in rasterizer.
- faster 1d-gaussian blur for shadow blur
- PDF/SVG generation (in addition to existing cairo integration)
- Add API for integrating device-N with RGB/CMYK through coloritto
- 32bit float coverage from rasterizer - right now we support 32f images; but composite them with 8bit alpha masks.
- More SIMD code (the common RGBA8 cases for AVX2 are the only bit
covered thus far, for floating point formats making the
existing code more autovectorizer friendly is a priority.)
- A GPU renderer, using pathfinder or similar HTML5 2d canvas matching library or even make ctx act as the cpu side
vertex and fragment input buffer cook for a GPU based approach.