Automatically choose correct barcode function.

Tests for barcode function.
This commit is contained in:
Michael Elsdörfer 2016-08-30 12:53:31 +02:00
parent a07f84a5bc
commit 5fa89ff685
3 changed files with 76 additions and 14 deletions

View File

@ -15,6 +15,9 @@ class NotSupported(Exception):
pass
BARCODE_B = 'barcodeB'
class BaseProfile(object):
"""This respresents a printer profile.
@ -43,6 +46,11 @@ class BaseProfile(object):
font = self.get_font(font)
return self.fonts[six.text_type(font)]['columns']
def supports(self, feature):
"""Return true/false for the given feature.
"""
return self.features.get(feature)
def get_profile(name=None, **kwargs):
"""Get the profile by name; if no name is given, return the
@ -84,10 +92,11 @@ def clean(s):
# For users, who want to provide their profile
class Profile(get_profile_class('default')):
def __init__(self, columns=None):
super(Profile, self).__init()
def __init__(self, columns=None, features={}):
super(Profile, self).__init__()
self.columns = columns
self.features = features
def get_columns(self, font):
if self.columns is not None:

View File

@ -23,7 +23,7 @@ from .exceptions import *
from abc import ABCMeta, abstractmethod # abstract base class support
from escpos.image import EscposImage
from escpos.capabilities import get_profile
from escpos.capabilities import get_profile, BARCODE_B
@six.add_metaclass(ABCMeta)
@ -293,7 +293,8 @@ class Escpos(object):
else:
raise CharCodeError()
def barcode(self, code, bc, height=64, width=3, pos="BELOW", font="A", align_ct=True, function_type="A"):
def barcode(self, code, bc, height=64, width=3, pos="BELOW", font="A",
align_ct=True, function_type=None):
""" Print Barcode
This method allows to print barcodes. The rendering of the barcode is done by the printer and therefore has to
@ -364,14 +365,40 @@ class Escpos(object):
issued.
:type align_ct: bool
:param function_type: Choose between ESCPOS function type A or B, depending on printer support and desired
barcode.
:param function_type: Choose between ESCPOS function type A or B,
depending on printer support and desired barcode. If not given,
the printer will attempt to automatically choose the correct
function based on the current profile.
*default*: A
:raises: :py:exc:`~escpos.exceptions.BarcodeSizeError`,
:py:exc:`~escpos.exceptions.BarcodeTypeError`,
:py:exc:`~escpos.exceptions.BarcodeCodeError`
"""
if function_type is None:
# Choose the function type automatically.
if bc in BARCODE_TYPES['A']:
function_type = 'A'
else:
if bc in BARCODE_TYPES['B']:
if not self.profile.supports(BARCODE_B):
raise BarcodeTypeError((
"Barcode type '{bc} not supported for "
"the current printer profile").format(bc=bc))
function_type = 'B'
else:
raise BarcodeTypeError((
"Barcode type '{bc} is not valid").format(bc=bc))
bc_types = BARCODE_TYPES[function_type.upper()]
if bc.upper() not in bc_types.keys():
raise BarcodeTypeError((
"Barcode type '{bc}' not valid for barcode function type "
"{function_type}").format(
bc=bc,
function_type=function_type,
))
# Align Bar Code()
if align_ct:
self._raw(TXT_ALIGN_CT)
@ -400,14 +427,6 @@ class Escpos(object):
else: # DEFAULT POSITION: BELOW
self._raw(BARCODE_TXT_BLW)
bc_types = BARCODE_TYPES[function_type.upper()]
if bc.upper() not in bc_types.keys():
# TODO: Raise a better error, or fix the message of this error type
raise BarcodeTypeError("Barcode type {bc} not valid for barcode function type {function_type}".format(
bc=bc,
function_type=function_type,
))
self._raw(bc_types[bc.upper()])
if function_type.upper() == "B":

View File

@ -0,0 +1,34 @@
#!/usr/bin/python
from __future__ import absolute_import
from __future__ import division
from __future__ import print_function
from __future__ import unicode_literals
import escpos.printer as printer
from escpos.constants import BARCODE_TYPE_A, BARCODE_TYPE_B
from escpos.capabilities import Profile, BARCODE_B
from escpos.exceptions import BarcodeTypeError
import pytest
@pytest.mark.parametrize("bctype,data,expected", [
('EAN13', '4006381333931',
b'\x1ba\x01\x1dh@\x1dw\x03\x1df\x00\x1dH\x02\x1dk\x024006381333931\x00')
])
def test_barcode(bctype, data, expected):
instance = printer.Dummy()
instance.barcode(data, bctype)
assert instance.output == expected
@pytest.mark.parametrize("bctype,supports_b", [
('invalid', True),
('CODE128', False),
])
def test_lacks_support(bctype, supports_b):
profile = Profile(features={BARCODE_B: supports_b})
instance = printer.Dummy(profile=profile)
with pytest.raises(BarcodeTypeError):
instance.barcode('test', bctype)
assert instance.output == ''