Source code for pystrich.code128

"""Code-128 barcode encoder

All needed by the user is done via the Code128Encoder class:

>>> encoder = Code128Encoder("HuDoRa")
>>> encoder.save("test.png")

Implemented by Helen Taylor for HUDORA GmbH.
Updated and ported to Python 3 by Michael Mulqueen for Method B Ltd.

Detailed documentation on the format here:
http://www.barcodeisland.com/code128.phtml
http://www.adams1.com/pub/russadam/128code.html

You may use this under a BSD License.
"""

from __future__ import annotations

import logging

from pystrich.bar_encoder import Bar1DEncoder
from pystrich.types import BarcodeRenderOptions

from .renderer import Code128Renderer
from .textencoder import TextEncoder

log = logging.getLogger("code128")


[docs] class Code128Encoder(Bar1DEncoder): """Encode a string as a Code 128 1D barcode. Code sets A, B and C are switched between automatically to minimise symbol length. The mod-103 checksum is computed and appended for you. Typical use:: encoder = Code128Encoder("nm0000385") encoder.save("barcode.png") :ivar text: The original input text. :ivar encoded_text: List of code values produced by the text encoder, including start codes and code-set switches. :ivar checksum: The mod-103 checksum value. :ivar bars: The bar/space pattern as a string of ``"1"`` and ``"0"``. :ivar options: Render-time options dict (empty if none were supplied). :ivar width: Pixel width of the most recently rendered image. ``0`` until a render method has been called. :ivar height: Pixel height of the most recently rendered image. """ options: BarcodeRenderOptions text: str encoded_text: list[int] checksum: int bars: str def __init__(self, text: str, options: BarcodeRenderOptions | None = None) -> None: """Encode ``text`` as Code 128 and compute the checksum. :param text: The data to encode. Any character in the Code 128 set (ASCII 0-127, plus the FNC controls via the dedicated text encoder) is permitted. :param options: Optional dict tweaking the rendered output. Supported keys: * ``ttf_font`` -- absolute path to a TrueType font for the label. Defaults to a bundled bitmap font. * ``ttf_fontsize`` -- font size in points. * ``show_label`` -- whether to render the human-readable label underneath the bars (defaults to ``True``). * ``height`` -- total image height in pixels (defaults to a third of the image width). * ``label_border`` -- pixels of space between barcode and label. * ``bottom_border`` -- pixels of space between label and the bottom edge. """ super().__init__(options) self.text = text encoder = TextEncoder() self.encoded_text = encoder.encode(self.text) log.debug("Encoded text is %s", self.encoded_text) self.checksum = self.calculate_check_sum() log.debug("Checksum is %d", self.checksum) self.bars = encoder.get_bars(self.encoded_text, self.checksum) log.debug("Bars: %s", self.bars)
[docs] def calculate_check_sum(self) -> int: """Compute the Code 128 mod-103 checksum for :attr:`encoded_text`. The start code contributes with weight 1; subsequent symbols are weighted by their 1-based position before the modulo is taken. """ checksum = self.encoded_text[0] for index, char in enumerate(self.encoded_text): if index > 0: checksum += index * char return checksum % 103
[docs] def init_renderer(self) -> Code128Renderer: """Construct a :class:`Code128Renderer` for the encoded bars. :rtype: :class:`Code128Renderer` """ return Code128Renderer(self.bars, self.text, self.options)