Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
11 changes: 11 additions & 0 deletions Lib/test/test_tkinter/test_font.py
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@
import collections.abc
import unittest
import tkinter
from tkinter import font
Expand Down Expand Up @@ -118,6 +119,16 @@ def test_repr(self):
repr(self.font), f'<tkinter.font.Font object {fontname!r}>'
)

def test_iterable_protocol(self):
self.assertNotIsSubclass(font.Font, collections.abc.Iterable)
self.assertNotIsSubclass(font.Font, collections.abc.Container)
self.assertNotIsInstance(self.font, collections.abc.Iterable)
self.assertNotIsInstance(self.font, collections.abc.Container)
with self.assertRaisesRegex(TypeError, 'is not iterable'):
iter(self.font)
with self.assertRaisesRegex(TypeError, 'is not a container or iterable'):
self.font in self.font


class DefaultRootTest(AbstractDefaultRootTest, unittest.TestCase):

Expand Down
52 changes: 30 additions & 22 deletions Lib/test/test_tkinter/test_images.py
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@
import collections.abc
import unittest
import tkinter
from test import support
Expand Down Expand Up @@ -61,7 +62,33 @@ def test_image_create_photo(self):
self.assertRaises(RuntimeError, tkinter.PhotoImage)


class BitmapImageTest(AbstractTkTest, unittest.TestCase):
class BaseImageTest:
def create(self):
return self.image_class('::img::test', master=self.root,
file=self.testfile)

def test_bug_100814(self):
# gh-100814: Passing a callable option value causes AttributeError.
with self.assertRaises(tkinter.TclError):
self.image_class('::img::test', master=self.root, spam=print)
image = self.image_class('::img::test', master=self.root)
with self.assertRaises(tkinter.TclError):
image.configure(spam=print)

def test_iterable_protocol(self):
image = self.create()
self.assertNotIsSubclass(self.image_class, collections.abc.Iterable)
self.assertNotIsSubclass(self.image_class, collections.abc.Container)
self.assertNotIsInstance(image, collections.abc.Iterable)
self.assertNotIsInstance(image, collections.abc.Container)
with self.assertRaisesRegex(TypeError, 'is not iterable'):
iter(image)
with self.assertRaisesRegex(TypeError, 'is not a container or iterable'):
image in image


class BitmapImageTest(BaseImageTest, AbstractTkTest, unittest.TestCase):
image_class = tkinter.BitmapImage

@classmethod
def setUpClass(cls):
Expand Down Expand Up @@ -144,26 +171,15 @@ def test_configure_foreground(self):
self.assertEqual(image['foreground'],
'-foreground {} {} #000000 yellow')

def test_bug_100814(self):
# gh-100814: Passing a callable option value causes AttributeError.
with self.assertRaises(tkinter.TclError):
tkinter.BitmapImage('::img::test', master=self.root, spam=print)
image = tkinter.BitmapImage('::img::test', master=self.root)
with self.assertRaises(tkinter.TclError):
image.configure(spam=print)


class PhotoImageTest(AbstractTkTest, unittest.TestCase):
class PhotoImageTest(BaseImageTest, AbstractTkTest, unittest.TestCase):
image_class = tkinter.PhotoImage

@classmethod
def setUpClass(cls):
AbstractTkTest.setUpClass.__func__(cls)
cls.testfile = support.findfile('python.gif', subdir='tkinterdata')

def create(self):
return tkinter.PhotoImage('::img::test', master=self.root,
file=self.testfile)

def colorlist(self, *args):
if tkinter.TkVersion >= 8.6 and self.wantobjects:
return args
Expand Down Expand Up @@ -282,14 +298,6 @@ def test_configure_palette(self):
image.configure(palette='3/4/2')
self.assertEqual(image['palette'], '3/4/2')

def test_bug_100814(self):
# gh-100814: Passing a callable option value causes AttributeError.
with self.assertRaises(tkinter.TclError):
tkinter.PhotoImage('::img::test', master=self.root, spam=print)
image = tkinter.PhotoImage('::img::test', master=self.root)
with self.assertRaises(tkinter.TclError):
image.configure(spam=print)

def test_blank(self):
image = self.create()
image.blank()
Expand Down
12 changes: 12 additions & 0 deletions Lib/test/test_tkinter/test_misc.py
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@
import collections.abc
import functools
import unittest
import tkinter
Expand Down Expand Up @@ -508,6 +509,17 @@ def test_embedded_null(self):
widget.selection_range(0, 'end')
self.assertEqual(widget.selection_get(), '\u20ac\0abc\x00def')

def test_iterable_protocol(self):
widget = tkinter.Entry(self.root)
self.assertNotIsSubclass(tkinter.Entry, collections.abc.Iterable)
self.assertNotIsSubclass(tkinter.Entry, collections.abc.Container)
self.assertNotIsInstance(widget, collections.abc.Iterable)
self.assertNotIsInstance(widget, collections.abc.Container)
with self.assertRaisesRegex(TypeError, 'is not iterable'):
iter(widget)
with self.assertRaisesRegex(TypeError, 'is not a container or iterable'):
widget in widget


class WmTest(AbstractTkTest, unittest.TestCase):

Expand Down
3 changes: 3 additions & 0 deletions Lib/tkinter/__init__.py
Original file line number Diff line number Diff line change
Expand Up @@ -1848,6 +1848,7 @@ def cget(self, key):
return self.tk.call(self._w, 'cget', '-' + key)

__getitem__ = cget
__iter__ = None # prevent using __getitem__ for iteration

def __setitem__(self, key, value):
self.configure({key: value})
Expand Down Expand Up @@ -4280,6 +4281,8 @@ def __setitem__(self, key, value):
def __getitem__(self, key):
return self.tk.call(self.name, 'configure', '-'+key)

__iter__ = None # prevent using __getitem__ for iteration

def configure(self, **kw):
"""Configure the image."""
res = ()
Expand Down
2 changes: 2 additions & 0 deletions Lib/tkinter/font.py
Original file line number Diff line number Diff line change
Expand Up @@ -114,6 +114,8 @@ def __getitem__(self, key):
def __setitem__(self, key, value):
self.configure(**{key: value})

__iter__ = None # prevent using __getitem__ for iteration

def __del__(self):
try:
if self.delete_font:
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
Improve error message when trying to iterate a Tk widget, image or font.
Loading