diff --git a/Lib/test/test_tkinter/test_font.py b/Lib/test/test_tkinter/test_font.py index ee147710fbfc85..fd1c814c0c26e9 100644 --- a/Lib/test/test_tkinter/test_font.py +++ b/Lib/test/test_tkinter/test_font.py @@ -130,6 +130,15 @@ def test_iterable_protocol(self): with self.assertRaisesRegex(TypeError, 'is not a container or iterable'): self.font in self.font + def test_negative_pixel_size(self): + # gh-143990: negative sizes (pixels) should be preserved in Font objects + pixel_size = -14 + f = font.Font(self.root, family='Helvetica', size=pixel_size) + self.assertEqual(f.cget("size"), pixel_size) + # Test initialization with font tuple + f2 = font.Font(self.root, font=('Helvetica', pixel_size)) + self.assertEqual(f2.cget("size"), pixel_size) + class DefaultRootTest(AbstractDefaultRootTest, unittest.TestCase): diff --git a/Lib/tkinter/font.py b/Lib/tkinter/font.py index 896e910d69f6f3..c1b58bffad2c8f 100644 --- a/Lib/tkinter/font.py +++ b/Lib/tkinter/font.py @@ -72,7 +72,21 @@ def __init__(self, root=None, font=None, name=None, exists=False, tk = getattr(root, 'tk', root) if font: # get actual settings corresponding to the given font - font = tk.splitlist(tk.call("font", "actual", font)) + font_opts = tk.splitlist(tk.call("font", "actual", font)) + #if input was passed as tuple, restore + # font actual will normalize negative (pixel) -> positive(points) + if isinstance(font, tuple) and len(font) >= 2: + # format=(family, size, styles) + req_size = font[1] + if isinstance(req_size, (int, float)): + opt=list(font_opts) + try: + i = opt.index('-size') + opt[i+1] = str(req_size) + font_opts = tuple(opt) + except ValueError: + pass + font = font_opts else: font = self._set(options) if not name: diff --git a/Misc/NEWS.d/next/Library/2026-01-18-15-07-12.gh-issue-143990.0_lU8l.rst b/Misc/NEWS.d/next/Library/2026-01-18-15-07-12.gh-issue-143990.0_lU8l.rst new file mode 100644 index 00000000000000..38a5157f862399 --- /dev/null +++ b/Misc/NEWS.d/next/Library/2026-01-18-15-07-12.gh-issue-143990.0_lU8l.rst @@ -0,0 +1,3 @@ +Preserve negative font sizes (pixels) in :class:`tkinter.font.Font` when +defined via a tuple. Previously, these were incorrectly normalized to +positive sizes (points) by Tcl's ``font actual`` command.