mirror of
https://github.com/python/cpython.git
synced 2025-09-22 08:23:36 +00:00
Issue #18592: Add unittests for SearchDialogBase. Patch by Phil Webster.
This commit is contained in:
parent
f5ac57dc05
commit
525168bd74
2 changed files with 213 additions and 10 deletions
|
@ -16,10 +16,12 @@ class SearchDialogBase:
|
||||||
(make_button, create_command_buttons).
|
(make_button, create_command_buttons).
|
||||||
These are bound to functions that execute the command.
|
These are bound to functions that execute the command.
|
||||||
|
|
||||||
Except for command buttons, this base class is not limited to
|
Except for command buttons, this base class is not limited to items
|
||||||
items common to all three subclasses. Rather, it is the Find dialog
|
common to all three subclasses. Rather, it is the Find dialog minus
|
||||||
minus the "Find Next" command and its execution function.
|
the "Find Next" command, its execution function, and the
|
||||||
The other dialogs override methods to replace and add widgets.
|
default_command attribute needed in create_widgets. The other
|
||||||
|
dialogs override attributes and methods, the latter to replace and
|
||||||
|
add widgets.
|
||||||
'''
|
'''
|
||||||
|
|
||||||
title = "Search Dialog" # replace in subclasses
|
title = "Search Dialog" # replace in subclasses
|
||||||
|
@ -30,9 +32,10 @@ class SearchDialogBase:
|
||||||
'''Initialize root, engine, and top attributes.
|
'''Initialize root, engine, and top attributes.
|
||||||
|
|
||||||
top (level widget): set in create_widgets() called from open().
|
top (level widget): set in create_widgets() called from open().
|
||||||
text (Text being searched): set in open(), only used in subclasses().
|
text (Text searched): set in open(), only used in subclasses().
|
||||||
ent (ry): created in make_entry() called from create_entry().
|
ent (ry): created in make_entry() called from create_entry().
|
||||||
row (of grid): 0 in create_widgets(), +1 in make_entry/frame().
|
row (of grid): 0 in create_widgets(), +1 in make_entry/frame().
|
||||||
|
default_command: set in subclasses, used in create_widgers().
|
||||||
|
|
||||||
title (of dialog): class attribute, override in subclasses.
|
title (of dialog): class attribute, override in subclasses.
|
||||||
icon (of dialog): ditto, use unclear if cannot minimize dialog.
|
icon (of dialog): ditto, use unclear if cannot minimize dialog.
|
||||||
|
@ -93,25 +96,27 @@ class SearchDialogBase:
|
||||||
e = Entry(self.top, textvariable=var, exportselection=0)
|
e = Entry(self.top, textvariable=var, exportselection=0)
|
||||||
e.grid(row=self.row, column=1, sticky="nwe")
|
e.grid(row=self.row, column=1, sticky="nwe")
|
||||||
self.row = self.row + 1
|
self.row = self.row + 1
|
||||||
return e
|
return l, e # return label for testing
|
||||||
|
|
||||||
def create_entries(self):
|
def create_entries(self):
|
||||||
"Create one or more entry lines with make_entry."
|
"Create one or more entry lines with make_entry."
|
||||||
self.ent = self.make_entry("Find:", self.engine.patvar)
|
self.ent = self.make_entry("Find:", self.engine.patvar)[1]
|
||||||
|
|
||||||
def make_frame(self,labeltext=None):
|
def make_frame(self,labeltext=None):
|
||||||
"Return gridded labeled Frame for option or other buttons."
|
"Return gridded labeled Frame for option or other buttons."
|
||||||
if labeltext:
|
if labeltext:
|
||||||
l = Label(self.top, text=labeltext)
|
l = Label(self.top, text=labeltext)
|
||||||
l.grid(row=self.row, column=0, sticky="nw")
|
l.grid(row=self.row, column=0, sticky="nw")
|
||||||
|
else:
|
||||||
|
l = ''
|
||||||
f = Frame(self.top)
|
f = Frame(self.top)
|
||||||
f.grid(row=self.row, column=1, columnspan=1, sticky="nwe")
|
f.grid(row=self.row, column=1, columnspan=1, sticky="nwe")
|
||||||
self.row = self.row + 1
|
self.row = self.row + 1
|
||||||
return f
|
return l, f
|
||||||
|
|
||||||
def create_option_buttons(self):
|
def create_option_buttons(self):
|
||||||
"Fill frame with Checkbuttons bound to SearchEngine booleanvars."
|
"Fill frame with Checkbuttons bound to SearchEngine booleanvars."
|
||||||
f = self.make_frame("Options")
|
f = self.make_frame("Options")[1]
|
||||||
|
|
||||||
btn = Checkbutton(f, anchor="w",
|
btn = Checkbutton(f, anchor="w",
|
||||||
variable=self.engine.revar,
|
variable=self.engine.revar,
|
||||||
|
@ -144,7 +149,7 @@ class SearchDialogBase:
|
||||||
|
|
||||||
def create_other_buttons(self):
|
def create_other_buttons(self):
|
||||||
"Fill frame with buttons tied to other options."
|
"Fill frame with buttons tied to other options."
|
||||||
f = self.make_frame("Direction")
|
f = self.make_frame("Direction")[1]
|
||||||
|
|
||||||
btn = Radiobutton(f, anchor="w",
|
btn = Radiobutton(f, anchor="w",
|
||||||
variable=self.engine.backvar, value=1,
|
variable=self.engine.backvar, value=1,
|
||||||
|
|
198
Lib/idlelib/idle_test/test_searchdialogbase.py
Normal file
198
Lib/idlelib/idle_test/test_searchdialogbase.py
Normal file
|
@ -0,0 +1,198 @@
|
||||||
|
'''Unittests for idlelib/SearchDialogBase.py
|
||||||
|
|
||||||
|
Coverage: 99%. The only thing not covered is inconsequential --
|
||||||
|
testing skipping of suite when self.needwrapbutton is false.
|
||||||
|
|
||||||
|
'''
|
||||||
|
import unittest
|
||||||
|
from test.support import requires
|
||||||
|
from tkinter import Tk, Toplevel, Frame, Label, BooleanVar, StringVar
|
||||||
|
from idlelib import SearchEngine as se
|
||||||
|
from idlelib import SearchDialogBase as sdb
|
||||||
|
from idlelib.idle_test.mock_idle import Func
|
||||||
|
from idlelib.idle_test.mock_tk import Var, Mbox
|
||||||
|
|
||||||
|
# The following could help make some tests gui-free.
|
||||||
|
# However, they currently make radiobutton tests fail.
|
||||||
|
##def setUpModule():
|
||||||
|
## # Replace tk objects used to initialize se.SearchEngine.
|
||||||
|
## se.BooleanVar = Var
|
||||||
|
## se.StringVar = Var
|
||||||
|
##
|
||||||
|
##def tearDownModule():
|
||||||
|
## se.BooleanVar = BooleanVar
|
||||||
|
## se.StringVar = StringVar
|
||||||
|
|
||||||
|
class SearchDialogBaseTest(unittest.TestCase):
|
||||||
|
|
||||||
|
@classmethod
|
||||||
|
def setUpClass(cls):
|
||||||
|
requires('gui')
|
||||||
|
cls.root = Tk()
|
||||||
|
|
||||||
|
@classmethod
|
||||||
|
def tearDownClass(cls):
|
||||||
|
cls.root.destroy()
|
||||||
|
del cls.root
|
||||||
|
|
||||||
|
def setUp(self):
|
||||||
|
self.engine = se.SearchEngine(self.root) # None also seems to work
|
||||||
|
self.dialog = sdb.SearchDialogBase(root=self.root, engine=self.engine)
|
||||||
|
|
||||||
|
def tearDown(self):
|
||||||
|
self.dialog.close()
|
||||||
|
|
||||||
|
def test_open_and_close(self):
|
||||||
|
# open calls create_widgets, which needs default_command
|
||||||
|
self.dialog.default_command = None
|
||||||
|
|
||||||
|
# Since text parameter of .open is not used in base class,
|
||||||
|
# pass dummy 'text' instead of tk.Text().
|
||||||
|
self.dialog.open('text')
|
||||||
|
self.assertEqual(self.dialog.top.state(), 'normal')
|
||||||
|
self.dialog.close()
|
||||||
|
self.assertEqual(self.dialog.top.state(), 'withdrawn')
|
||||||
|
|
||||||
|
self.dialog.open('text', searchphrase="hello")
|
||||||
|
self.assertEqual(self.dialog.ent.get(), 'hello')
|
||||||
|
self.dialog.close()
|
||||||
|
|
||||||
|
def test_create_widgets(self):
|
||||||
|
self.dialog.create_entries = Func()
|
||||||
|
self.dialog.create_option_buttons = Func()
|
||||||
|
self.dialog.create_other_buttons = Func()
|
||||||
|
self.dialog.create_command_buttons = Func()
|
||||||
|
|
||||||
|
self.dialog.default_command = None
|
||||||
|
self.dialog.create_widgets()
|
||||||
|
|
||||||
|
self.assertTrue(self.dialog.create_entries.called)
|
||||||
|
self.assertTrue(self.dialog.create_option_buttons.called)
|
||||||
|
self.assertTrue(self.dialog.create_other_buttons.called)
|
||||||
|
self.assertTrue(self.dialog.create_command_buttons.called)
|
||||||
|
|
||||||
|
def test_make_entry(self):
|
||||||
|
equal = self.assertEqual
|
||||||
|
self.dialog.row = 0
|
||||||
|
self.dialog.top = Toplevel(self.root)
|
||||||
|
label, entry = self.dialog.make_entry("Test:", 'hello')
|
||||||
|
equal(label.cget('text'), 'Test:')
|
||||||
|
|
||||||
|
self.assertIn(entry.get(), 'hello')
|
||||||
|
egi = entry.grid_info()
|
||||||
|
equal(egi['row'], 0)
|
||||||
|
equal(egi['column'], 1)
|
||||||
|
equal(egi['rowspan'], 1)
|
||||||
|
equal(egi['columnspan'], 1)
|
||||||
|
equal(self.dialog.row, 1)
|
||||||
|
|
||||||
|
def test_create_entries(self):
|
||||||
|
self.dialog.row = 0
|
||||||
|
self.engine.setpat('hello')
|
||||||
|
self.dialog.create_entries()
|
||||||
|
self.assertIn(self.dialog.ent.get(), 'hello')
|
||||||
|
|
||||||
|
def test_make_frame(self):
|
||||||
|
self.dialog.row = 0
|
||||||
|
self.dialog.top = Toplevel(self.root)
|
||||||
|
label, frame = self.dialog.make_frame()
|
||||||
|
self.assertEqual(label, '')
|
||||||
|
self.assertIsInstance(frame, Frame)
|
||||||
|
|
||||||
|
label, labelledframe = self.dialog.make_frame('testlabel')
|
||||||
|
self.assertEqual(label.cget('text'), 'testlabel')
|
||||||
|
self.assertIsInstance(labelledframe, Frame)
|
||||||
|
|
||||||
|
def btn_test_setup(self, which):
|
||||||
|
self.dialog.row = 0
|
||||||
|
self.dialog.top = Toplevel(self.root)
|
||||||
|
if which == 'option':
|
||||||
|
self.dialog.create_option_buttons()
|
||||||
|
elif which == 'other':
|
||||||
|
self.dialog.create_other_buttons()
|
||||||
|
else:
|
||||||
|
raise ValueError('bad which arg %s' % which)
|
||||||
|
|
||||||
|
def test_create_option_buttons(self):
|
||||||
|
self.btn_test_setup('option')
|
||||||
|
self.checkboxtests()
|
||||||
|
|
||||||
|
def test_create_option_buttons_flipped(self):
|
||||||
|
for var in ('revar', 'casevar', 'wordvar', 'wrapvar'):
|
||||||
|
Var = getattr(self.engine, var)
|
||||||
|
Var.set(not Var.get())
|
||||||
|
self.btn_test_setup('option')
|
||||||
|
self.checkboxtests(flip=1)
|
||||||
|
|
||||||
|
def checkboxtests(self, flip=0):
|
||||||
|
"""Tests the four checkboxes in the search dialog window."""
|
||||||
|
engine = self.engine
|
||||||
|
for child in self.dialog.top.winfo_children():
|
||||||
|
for grandchild in child.winfo_children():
|
||||||
|
text = grandchild.config()['text'][-1]
|
||||||
|
if text == ('Regular', 'expression'):
|
||||||
|
self.btnstatetest(grandchild, engine.revar, flip)
|
||||||
|
elif text == ('Match', 'case'):
|
||||||
|
self.btnstatetest(grandchild, engine.casevar, flip)
|
||||||
|
elif text == ('Whole', 'word'):
|
||||||
|
self.btnstatetest(grandchild, engine.wordvar, flip)
|
||||||
|
elif text == ('Wrap', 'around'):
|
||||||
|
self.btnstatetest(grandchild, engine.wrapvar, not flip)
|
||||||
|
|
||||||
|
def btnstatetest(self, button, var, defaultstate):
|
||||||
|
self.assertEqual(var.get(), defaultstate)
|
||||||
|
if defaultstate == 1:
|
||||||
|
button.deselect()
|
||||||
|
else:
|
||||||
|
button.select()
|
||||||
|
self.assertEqual(var.get(), 1 - defaultstate)
|
||||||
|
|
||||||
|
def test_create_other_buttons(self):
|
||||||
|
self.btn_test_setup('other')
|
||||||
|
self.radiobuttontests()
|
||||||
|
|
||||||
|
def test_create_other_buttons_flipped(self):
|
||||||
|
self.engine.backvar.set(1)
|
||||||
|
self.btn_test_setup('other')
|
||||||
|
self.radiobuttontests(back=1)
|
||||||
|
|
||||||
|
def radiobuttontests(self, back=0):
|
||||||
|
searchupbtn = None
|
||||||
|
searchdownbtn = None
|
||||||
|
|
||||||
|
for child in self.dialog.top.winfo_children():
|
||||||
|
for grandchild in child.children.values():
|
||||||
|
text = grandchild.config()['text'][-1]
|
||||||
|
if text == 'Up':
|
||||||
|
searchupbtn = grandchild
|
||||||
|
elif text == 'Down':
|
||||||
|
searchdownbtn = grandchild
|
||||||
|
|
||||||
|
# Defaults to searching downward
|
||||||
|
self.assertEqual(self.engine.backvar.get(), back)
|
||||||
|
if back:
|
||||||
|
searchdownbtn.select()
|
||||||
|
else:
|
||||||
|
searchupbtn.select()
|
||||||
|
self.assertEqual(self.engine.backvar.get(), not back)
|
||||||
|
searchdownbtn.select()
|
||||||
|
|
||||||
|
def test_make_button(self):
|
||||||
|
self.dialog.top = Toplevel(self.root)
|
||||||
|
self.dialog.buttonframe = Frame(self.dialog.top)
|
||||||
|
btn = self.dialog.make_button('Test', self.dialog.close)
|
||||||
|
self.assertEqual(btn.cget('text'), 'Test')
|
||||||
|
|
||||||
|
def test_create_command_buttons(self):
|
||||||
|
self.dialog.create_command_buttons()
|
||||||
|
# Look for close button command in buttonframe
|
||||||
|
closebuttoncommand = ''
|
||||||
|
for child in self.dialog.buttonframe.winfo_children():
|
||||||
|
if child.config()['text'][-1] == 'close':
|
||||||
|
closebuttoncommand = child.config()['command'][-1]
|
||||||
|
self.assertIn('close', closebuttoncommand)
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
unittest.main(verbosity=2, exit=2)
|
Loading…
Add table
Add a link
Reference in a new issue