diff --git a/src/font16seg.py b/src/font16seg.py index c863eb0..3969f84 100644 --- a/src/font16seg.py +++ b/src/font16seg.py @@ -362,3 +362,18 @@ def text(x, y, txt, *, color=None, unlit_color=None): x -= delta elif _rotate == 270: y -= delta + +def assign(code, flags): + """ + Assign a glyph to a specific character code. + + Parameters + ---------- + code : int + Character code to assign the glyph. + flags : int + 16-bit flags which segment is to be lit. + """ + if flags < 0 or flags > 0b1111111111111111: + raise ValueError('flags must be in the range of 0-65535') + __CHARACTERS[code] = (__TYPE_16SEG, flags) diff --git a/tests/test_font16seg.py b/tests/test_font16seg.py index d2fc1be..5c829da 100644 --- a/tests/test_font16seg.py +++ b/tests/test_font16seg.py @@ -196,3 +196,62 @@ def test_textWidth_with_period(self): def test_textWidth_with_period_only(self): font16seg.attrib16seg(10, 8, lcd.WHITE, letter_spacing=1) self.assertEqual(font16seg.textWidth("."), 8) + + def test_assign(self): + lcd.screensize = MagicMock(return_value=(136, 241)) + lcd.triangle = MagicMock() + lcd.rect = MagicMock() + + font16seg.attrib16seg(8, 2, lcd.WHITE, unlit_color=None) + font16seg.assign(ord("d"), 0b0000001111000111) + font16seg.text(0, 0, "d") + self.assertEqual(lcd.triangle.call_count, 14) + self.assertEqual(lcd.rect.call_count, 7) + + def test_assign_min(self): + lcd.screensize = MagicMock(return_value=(136, 241)) + lcd.triangle = MagicMock() + lcd.rect = MagicMock() + + font16seg.attrib16seg(8, 2, lcd.WHITE, unlit_color=None) + font16seg.assign(ord("x"), 0) + font16seg.text(0, 0, "x") + lcd.triangle.assert_not_called() + lcd.rect.assert_not_called() + + def test_assign_max(self): + lcd.screensize = MagicMock(return_value=(136, 241)) + lcd.triangle = MagicMock() + lcd.rect = MagicMock() + + font16seg.attrib16seg(8, 2, lcd.WHITE, unlit_color=None) + font16seg.assign(ord("x"), 0b1111111111111111) + font16seg.text(0, 0, "x") + self.assertEqual(lcd.triangle.call_count, 32) + self.assertEqual(lcd.rect.call_count, 12) + + def test_assign_out_of_range(self): + with self.assertRaises(ValueError): + font16seg.assign(ord("x"), -1) + + with self.assertRaises(ValueError): + font16seg.assign(ord("x"), 0b10000000000000000) + + def test_assign_overwrite(self): + lcd.screensize = MagicMock(return_value=(136, 241)) + lcd.triangle = MagicMock() + lcd.rect = MagicMock() + + font16seg.attrib16seg(8, 2, lcd.WHITE, unlit_color=None) + + font16seg.text(0, 0, "1") + self.assertEqual(lcd.triangle.call_count, 4) + self.assertEqual(lcd.rect.call_count, 2) + + lcd.triangle.reset_mock() + lcd.rect.reset_mock() + + font16seg.assign(ord("1"), 0b1000100000010011) + font16seg.text(0, 0, "1") + self.assertEqual(lcd.triangle.call_count, 10) + self.assertEqual(lcd.rect.call_count, 5)