+class WinfoTest(AbstractTkTest, unittest.TestCase):
+
+ def test_winfo_rgb(self):
+
+ def assertApprox(col1, col2):
+ # A small amount of flexibility is required (bpo-45496)
+ # 33 is ~0.05% of 65535, which is a reasonable margin
+ for col1_channel, col2_channel in zip(col1, col2):
+ self.assertAlmostEqual(col1_channel, col2_channel, delta=33)
+
+ root = self.root
+ rgb = root.winfo_rgb
+
+ # Color name.
+ self.assertEqual(rgb('red'), (65535, 0, 0))
+ self.assertEqual(rgb('dark slate blue'), (18504, 15677, 35723))
+ # #RGB - extends each 4-bit hex value to be 16-bit.
+ self.assertEqual(rgb('#F0F'), (0xFFFF, 0x0000, 0xFFFF))
+ # #RRGGBB - extends each 8-bit hex value to be 16-bit.
+ assertApprox(rgb('#4a3c8c'), (0x4a4a, 0x3c3c, 0x8c8c))
+ # #RRRRGGGGBBBB
+ assertApprox(rgb('#dede14143939'), (0xdede, 0x1414, 0x3939))
+ # Invalid string.
+ with self.assertRaises(tkinter.TclError):
+ rgb('#123456789a')
+ # RGB triplet is invalid input.
+ with self.assertRaises(tkinter.TclError):
+ rgb((111, 78, 55))
+
+ def test_winfo_pathname(self):
+ t = tkinter.Toplevel(self.root)
+ w = tkinter.Button(t)
+ wid = w.winfo_id()
+ self.assertIsInstance(wid, int)
+ self.assertEqual(self.root.winfo_pathname(hex(wid)), str(w))
+ self.assertEqual(self.root.winfo_pathname(hex(wid), displayof=None), str(w))
+ self.assertEqual(self.root.winfo_pathname(hex(wid), displayof=t), str(w))
+ self.assertEqual(self.root.winfo_pathname(wid), str(w))
+ self.assertEqual(self.root.winfo_pathname(wid, displayof=None), str(w))
+ self.assertEqual(self.root.winfo_pathname(wid, displayof=t), str(w))
+
+ def test_winfo_class_name_parent(self):
+ f = tkinter.Frame(self.root)
+ b = tkinter.Button(f)
+ self.assertEqual(f.winfo_class(), 'Frame')
+ self.assertEqual(b.winfo_class(), 'Button')
+ self.assertEqual(b.winfo_name(), str(b).rsplit('.', 1)[-1])
+ self.assertEqual(b.winfo_parent(), str(f))
+ self.assertEqual(f.winfo_parent(), str(self.root))
+ self.assertIs(f.winfo_toplevel(), self.root)
+ t = tkinter.Toplevel(self.root)
+ self.assertIs(tkinter.Button(t).winfo_toplevel(), t)
+ self.assertEqual(self.root.nametowidget(b.winfo_parent()), f)
+
+ def test_winfo_children(self):
+ self.assertEqual(self.root.winfo_children(), [])
+ f = tkinter.Frame(self.root)
+ b = tkinter.Button(f)
+ self.assertEqual(self.root.winfo_children(), [f])
+ self.assertEqual(f.winfo_children(), [b])
+
+ def test_winfo_visual_info(self):
+ f = tkinter.Frame(self.root)
+ self.assertIsInstance(f.winfo_depth(), int)
+ self.assertIsInstance(f.winfo_cells(), int)
+ self.assertIsInstance(f.winfo_visual(), str)
+ self.assertIsInstance(f.winfo_visualid(), str)
+ self.assertIsInstance(f.winfo_colormapfull(), bool)
+ visuals = self.root.winfo_visualsavailable()
+ self.assertIsInstance(visuals, list)
+ for name, depth in visuals:
+ self.assertIsInstance(name, str)
+ self.assertIsInstance(depth, int)
+
+ def test_winfo_viewable(self):
+ f = tkinter.Frame(self.root)
+ self.assertFalse(f.winfo_viewable())
+ f.pack()
+ f.wait_visibility()
+ self.root.update()
+ self.assertTrue(f.winfo_viewable())
+
+ def test_winfo_atom(self):
+ atom = self.root.winfo_atom('PRIMARY')
+ self.assertIsInstance(atom, int)
+ self.assertEqual(self.root.winfo_atomname(atom), 'PRIMARY')
+ self.assertEqual(
+ self.root.winfo_atomname(atom, displayof=self.root), 'PRIMARY')
+ self.assertEqual(
+ self.root.winfo_atom('PRIMARY', displayof=self.root), atom)
+ self.assertRaisesRegex(TclError, 'no atom exists',
+ self.root.winfo_atomname, 10 ** 9)
+
+ def test_winfo_pointer(self):
+ self.assertIsInstance(self.root.winfo_pointerx(), int)
+ self.assertIsInstance(self.root.winfo_pointery(), int)
+ xy = self.root.winfo_pointerxy()
+ self.assertIsInstance(xy, tuple)
+ self.assertEqual(len(xy), 2)
+ self.assertTrue(all(isinstance(v, int) for v in xy))
+
+ def test_winfo_containing(self):
+ self.root.update()
+ # No window contains a point far off the screen.
+ self.assertIsNone(self.root.winfo_containing(-10000, -10000))
+ self.assertIsNone(
+ self.root.winfo_containing(-10000, -10000, displayof=self.root))
+
+ def test_winfo_fpixels(self):
+ self.assertIsInstance(self.root.winfo_fpixels('1i'), float)
+ self.assertAlmostEqual(self.root.winfo_fpixels('1i'),
+ self.root.winfo_fpixels('72p'))
+ # Tk < 9 reports 'bad screen distance "spam"', Tk 9 reports
+ # 'expected screen distance ... but got "spam"'.
+ self.assertRaisesRegex(TclError,
+ r'(bad|expected) screen distance.*"spam"',
+ self.root.winfo_fpixels, 'spam')
+
+ def test_winfo_screen(self):
+ for name in ('winfo_screenwidth', 'winfo_screenheight',
+ 'winfo_screenmmwidth', 'winfo_screenmmheight',
+ 'winfo_screencells', 'winfo_screendepth'):
+ value = getattr(self.root, name)()
+ self.assertIsInstance(value, int)
+ self.assertGreater(value, 0)
+ self.assertIsInstance(self.root.winfo_screenvisual(), str)
+ self.assertIsInstance(self.root.winfo_screen(), str)
+ self.assertIsInstance(self.root.winfo_server(), str)
+
+ def test_winfo_vroot(self):
+ for name in ('winfo_vrootwidth', 'winfo_vrootheight',
+ 'winfo_vrootx', 'winfo_vrooty'):
+ self.assertIsInstance(getattr(self.root, name)(), int)
+
+ def test_winfo_interps(self):
+ interps = self.root.winfo_interps()
+ self.assertIsInstance(interps, tuple)
+ # The registry of interpreters is only populated where "send" is
+ # supported (i.e. X11), so do not require this interpreter's name.
+ if self.root._windowingsystem == 'x11':
+ self.assertIn(self.root.tk.call('tk', 'appname'), interps)
+ self.assertEqual(self.root.winfo_interps(displayof=self.root), interps)
+
+