tim
Fork of https://codeberg.org/chuvok/tim.h
about
tim is a portable library to create simple terminal applications Demo video: https://asciinema.org/a/zn3p0dsVCOQOzwY1S9gDfyaxQ
build
-
Clone this repository.
git clone https://timerix.ddns.net/git/Timerix/tim.git -
Install cbuild. Select latest version compatible with the one in
project.config. Example: For2.3.2download latest2.3.x. -
Build static library
cd tim cbuild build_static_lib -
Build tests and examples
cbuild ask hello snek test color string
quick start
See example/hello.c
layout
The terminal's columns (x) and rows (y) are addressed by their coordinates, the origin is in the top left corner.
Scopes are the primary layout mechanism. They are used to group and place multiple elements. Scopes can be nested.
The root scope is the full terminal screen. The scope macro is constructed with a for loop, so statements like break or return inside the scope block will probably give you a bad time.
Elements (widget, control, component) are elements of user interaction, such as a button or edit box. Most elements take x/y/w/h arguments to control placement. All positions are given in relation the element's parent scope.
Automatic (A) width and height are either based on the element's content, or take the full available space from parent.
| arg | value | placement |
|---|---|---|
| x | n | n columns to left |
| x | ~n | n columns to right |
| x | A | center horizontally |
| y | n | n rows to top |
| y | ~n | n rows to bottom |
| y | A | center vertically |
| w | n | n columns wide |
| w | ~n | fit width to n columns to right |
| w | A | automatic width |
| h | n | n rows high |
| h | ~n | fit height n rows to bottom |
| h | A | automatic height |
The layout automatically adopts to terminal window resize events.
colors
Colors are stored as 8-bit values.
Most terminals support 16 ANSI colors. You can see them in TimColor16 enum.
It's better to use xterm256 colors istead, because ANSI colors look different in each terminal.
https://www.ditig.com/256-colors-cheat-sheet

events
tim_run blocks until it observes an event. Mouse and key events are always immediately followed by a draw event in order to make changes visible.
Some elements need to consume events, for example edit consumes the key event when focused in order to prevent other key handlers on acting on them.
The current event is stored in tim->event.
elements
frame (x, y, w, h, color)
Draw an empty frame and fill area.
x/y/w/h see layout documentation
style background, frame
label (str, x, y, w, h, color)
Draw text label. Automatic width and height are supported. Strings
exceeding width or height are clipped.
str zero terminated string
x/y/w/h see layout documentation
style background, text
button (str, x, y, w, h, color) -> bool
Draw button. Automatic width and height are supported. Strings exceeding
width or height are clipped. Returns true when clicked.
str zero terminated string
x/y/w/h see layout documentation
style frame, background, text
edit (state, x, y, w, color) -> int
Draw text edit. Output is stored in state.s.
Receives input events when focused by mouse click or by setting focus manually.
Escape or return relinquish focus.
Returns key id if received key input.
state pointer to persistent edit state struct
x/y/w see layout documentation
style f rame, background, text
check (str, state, x, y, w, color) -> bool
Draw check box. State determines how the box is checked. [x] when state
is non-zero, [ ] when state is zero, [-] when state is -1. A mouse click
toggles the state between one and zero and returns true.
str zero terminated string
state pointer to persistent state variable
x/y/w see layout documentation
style check, background, text
radio (str, state, v, x, y, w, color) -> bool
Draw radio box. If state equals v, the box is selected. Radios are
grouped through a shared state. Within that group, each v must be unique.
A mouse click assigns v to state and returns true.
str zero terminated string
state pointer to persistent state variable
v unique state value
x/y/w see layout documentation
style radio, background, text
functions
tim_run (fps) -> bool
Process events and render frame. Blocks until input is received or the
next frame is due. First call also initializes the terminal. When fps is
zero the function blocks until input is received. Key and mouse events
are immediately followed by a draw event, so the actual fps can be
significantly greater than requested. Always returns true. To reset the
terminal after a crash, run "reset".
The Ctrl-C interrupt is masked, so make sure to put an exit condition
like this at the end of the main loop:
if (tim_is_key_press(ESCAPE_KEY))
exit(0);
fps frames per second
tim_is_key_press (key) -> bool
Returns true if key was pressed.
key char literal or one of the KEY constants, see constants
tim_time_usec () -> int64
Returns monotonic clock value in microseconds. Not affected by summer
time or leap seconds.
useful links
https://invisible-island.net/xterm/ctlseqs/ctlseqs.html https://learn.microsoft.com/en-us/windows/console/
bugs
- If Enter key doesn't work as expected on linux, write
stty saneto~/.profile. It will change terminal settings from insane to sane xD - Double buffering is still new, set ENABLE_DBUF to 0 if you see glitches
- Double width characters like 彁 are not fully supported. Terminals do not handle these consistently and there is no portable way to reliably determine character width. The renderer can deal with some of the problems caused by this, but results may vary.
- Decomposed (NFD) UTF-8 is not supported and will cause havoc
- Zero width code points are not supported
- Windows cmd.exe resize events may be delayed
compatibility
| emulator | support | remarks |
|---|---|---|
| Alacritty | ? | |
| cmd.exe | good | resize may lag |
| Cool Retro Term | good | wide character spill |
| Deepin Terminal | good | wide character spill |
| Eterm | abysmal | garbled output |
| GNOME Terminal | full | |
| GNUstep Terminal | abysmal | garbled output |
| iTerm2 | ? | |
| kitty | full | |
| Konsole | full | |
| LXTerminal | full | |
| macOS Terminal | ? | |
| PuTTY | full | |
| QTerminal | good | wide character spill |
| rxvt-unicode | full | |
| GNU Screen | good | no alternate buffer, double esc |
| st | full | |
| Terminator | full | |
| Terminology | full | |
| tmux | good | esc lags |
| Windows Terminal | full | |
| Xfce Terminal | full | |
| XTerm | full | XTerm is law |
| Zutty | full |
license
MIT License
Copyright (c) MMXXIV Chu'vok chuvok@maeppi.e4ward.com
Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions:
The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software.
The software is provided "as is", without warranty of any kind, express or implied, including but not limited to the warranties of merchantability, fitness for a particular purpose and noninfringement. In no event shall the authors or copyright holders be liable for any claim, damages or other liability, whether in an action of contract, tort or otherwise, arising from, out of or in connection with the software or the use or other dealings in the software.