Tutorial#

This is a basic introduction to using the library. Please refer to the API Reference for detailed description of the features and functionality provided by the library.

For this tutorial we’ll be using the image below:

../_images/python.png

The image has a resolution of 288x288 pixels.

Note

All the samples in this tutorial occurred in a terminal window of 255 columns by 70 lines.

Creating an Instance#

Image instances can be created using the convenience functions AutoImage(), from_file() and from_url(), which automatically detect the best style supported by the terminal emulator.

Instances can also be created using the Image Classes directly via their respective constructors or from_file() and from_url() methods.

  1. Initialize with a file path:

    from term_image.image import from_file
    
    image = from_file("path/to/python.png")
    
  2. Initialize with a URL:

    from term_image.image import from_url
    
    image = from_url("https://raw.githubusercontent.com/AnonymouX47/term-image/main/docs/source/resources/tutorial/python.png")
    
  3. Initialize with a PIL (Pillow) image instance:

    from PIL import Image
    from term_image.image import AutoImage
    
    img = Image.open("path/to/python.png")
    image = AutoImage(img)
    

Rendering an Image#

Rendering an image is the process of converting it (per-frame for animated images) into text (a string) which reproduces a representation or approximation of the image when written to the terminal.

Hint

To display the rendered image in the following steps, pass the string as an argument to print().

There are two ways to render an image:

Unformatted Rendering#

This is done using:

str(image)

The image is rendered without padding/alignment and with transparency enabled.

The output (using print()) should look like:

../_images/str.png

Formatted Rendering#

Note

To see the effect of alignment in the steps below, set the image size smaller than your terminal size, with e.g:

image.height = 50

This sets the image height to 50 lines (which is less than 70, the height of the terminal window used to prepare this tutorial) and the width proportionally.

We’ll see more about this later.

Below are examples of formatted rendering:

format(image, "|200.^70#ffffff")

Renders the image with:

Note

You might have to reduce the padding width (200) and/or height (70) to something that’ll fit into your terminal window, or increase the size of the terminlal window

The output (using print()) should look like:

../_images/white_bg.png

f"{image:>._#.5}"

Renders the image with:

The output (using print()) should look like:

../_images/alpha_0_5.png

"{:1.1#}".format(image)

Renders the image with:

  • center horizontal alignment (default)

  • no horizontal padding, since 1 is less than or equal to the image width

  • middle vertical alignment (default)

  • no vertical padding, since 1 is less than or equal to the image height

  • transparency is disabled (alpha channel is ignored)

The output (using print()) should look like:

../_images/no_alpha_no_align.png

Drawing/Displaying an Image#

There are two basic ways to draw an image to the terminal screen:

  1. Using the draw() method:

    image.draw()
    

    NOTE: draw() has various parameters for Render Formatting.

  2. Using print() with an image render output (i.e printing the rendered string):

    print(image)  # Uses str()
    # OR
    print(f"{image:>200.^70#ffffff}")  # Uses format()
    

Note

  • For animated images, only the former animates the output, the latter only draws the current frame (see seek() and tell()).

  • Also, the former performs size validation to see if the image will fit into the terminal, while the latter doesn’t.

Important

All the examples above use dynamic and automatic sizing.

Image Size#

The size of an image determines the dimension of its render output.
The image size can be retrieved via the size, width and height properties.

The size of an image can be in either of two states:

  1. Fixed

    In this state,

    • the size property evaluates to a 2-tuple of integers, while the width and height properties evaluate to integers,

    • the image is rendered with the set size.

  2. Dynamic

    In this state,

    • the size, width and height properties evaluate to a Size enum member,

    • the size with which the image is rendered is automatically calculated (based on the current terminal size or the image’s original size) whenever the image is to be rendered.

The size of an image can be set at instantiation by passing an integer or a Size enum member to either the width or the height keyword-only parameter. For whichever axis a dimension is given, the dimension on the other axis is calculated proportionally.

Note

  1. The arguments can only be given by keyword.

  2. If neither is given, the FIT dynamic size applies.

  3. All methods of instantiation accept these arguments.

For example:

>>> from term_image.image import Size, from_file
>>> image = from_file("python.png")  # Dynamic FIT
>>> image.size is Size.FIT
True
>>> image = from_file("python.png", width=60)  # Fixed
>>> image.size
(60, 30)
>>> image.height
30
>>> image = from_file("python.png", height=56)  # Fixed
>>> image.size
(112, 56)
>>> image.width
112
>>> image = from_file("python.png", height=Size.FIT)  # Fixed FIT
>>> image.size
(136, 68)
>>> image = from_file("python.png", width=Size.FIT_TO_WIDTH)  # Fixed FIT_TO_WIDTH
>>> image.size
(255, 128)
>>> image = from_file("python.png", height=Size.ORIGINAL)  # Fixed ORIGINAL
>>> image.size
(288, 144)

No size validation is performed i.e the resulting size might not fit into the terminal window

>>> image = from_file("python.png", height=68)  # Will fit in, OK
>>> image.size
(136, 68)
>>> image = from_file("python.png", height=500)  # Will not fit in, also OK
>>> image.size
(1000, 500)

An exception is raised when both width and height are given.

>>> image = from_file("python.png", width=100, height=100)
Traceback (most recent call last):
  .
  .
  .
ValueError: Cannot specify both width and height

The width and height properties can be used to set the size of an image after instantiation, resulting in fixed size.

>>> image = from_file("python.png")
>>> image.width = 56
>>> image.size
(56, 28)
>>> image.height
28
>>> image.height = 68
>>> image.size
(136, 68)
>>> image.width
136
>>> # Even though the terminal can't contain the resulting height, the size is still set
>>> image.width = 200
>>> image.size
(200, 100)
>>> image.width = Size.FIT
>>> image.size
(136, 69)
>>> image.height = Size.FIT_TO_WIDTH
>>> image.size
(255, 128)
>>> image.height = Size.ORIGINAL
>>> image.size
(288, 144)

The size property can only be set to a Size enum member, resulting in dynamic size.

>>> image = from_file("python.png")
>>> image.size = Size.FIT
>>> image.size is image.width is image.height is Size.FIT
True
>>> image.size = Size.FIT_TO_WIDTH
>>> image.size is image.width is image.height is Size.FIT_TO_WIDTH
True
>>> image.size = Size.ORIGINAL
>>> image.size is image.width is image.height is Size.ORIGINAL
True

Important

  1. The currently set cell ratio is also taken into consideration when calculating sizes for images of Text-based Render Styles.

  2. There is a 2-line difference between the default frame size and the terminal size to allow for shell prompts and the likes.

Tip

See set_size() for extended sizing control.


To explore more of the library’s features and functionality, check out the User Guide and the API Reference.