blob: adee326e1deb9149f70130b9b44b5cf306b3a96e [file] [log] [blame]
Kurt B. Kaiser09cb74b2003-06-12 04:20:56 +00001"""Simple text browser for IDLE
2
Steven M. Gava44d3d1a2001-07-31 06:59:02 +00003"""
Georg Brandl14fc4272008-05-17 18:39:55 +00004from tkinter import *
Terry Jan Reedy01e35752016-06-10 18:19:21 -04005from tkinter.ttk import Scrollbar
Terry Jan Reedy82c46152016-06-22 04:54:18 -04006from tkinter.messagebox import showerror
Steven M. Gava44d3d1a2001-07-31 06:59:02 +00007
Terry Jan Reedybfbaa6b2016-08-31 00:50:55 -04008
Steven M. Gava44d3d1a2001-07-31 06:59:02 +00009class TextViewer(Toplevel):
Terry Jan Reedya3623c82016-08-31 19:45:39 -040010 "A simple text viewer dialog for IDLE."
Kurt B. Kaiser09cb74b2003-06-12 04:20:56 +000011
Terry Jan Reedy1b392ff2014-05-24 18:48:18 -040012 def __init__(self, parent, title, text, modal=True, _htest=False):
Guido van Rossum8ce8a782007-11-01 19:42:39 +000013 """Show the given text in a scrollable window with a 'close' button
14
Terry Jan Reedy537e2c82014-06-05 03:38:34 -040015 If modal option set to False, user can interact with other windows,
16 otherwise they will be unable to interact with other windows until
17 the textview window is closed.
18
19 _htest - bool; change box location when running htest.
Steven M. Gavad721c482001-07-31 10:46:53 +000020 """
21 Toplevel.__init__(self, parent)
22 self.configure(borderwidth=5)
Terry Jan Reedya3623c82016-08-31 19:45:39 -040023 # Place dialog below parent if running htest.
Terry Jan Reedyd0cadba2015-10-11 22:07:31 -040024 self.geometry("=%dx%d+%d+%d" % (750, 500,
Terry Jan Reedy1b392ff2014-05-24 18:48:18 -040025 parent.winfo_rootx() + 10,
26 parent.winfo_rooty() + (10 if not _htest else 100)))
Terry Jan Reedya3623c82016-08-31 19:45:39 -040027 # TODO: get fg/bg from theme.
Kurt B. Kaiser09cb74b2003-06-12 04:20:56 +000028 self.bg = '#ffffff'
29 self.fg = '#000000'
Steven M. Gava44d3d1a2001-07-31 06:59:02 +000030
Steven M. Gavad721c482001-07-31 10:46:53 +000031 self.CreateWidgets()
32 self.title(title)
Steven M. Gavad721c482001-07-31 10:46:53 +000033 self.protocol("WM_DELETE_WINDOW", self.Ok)
34 self.parent = parent
35 self.textView.focus_set()
Terry Jan Reedya3623c82016-08-31 19:45:39 -040036 # Bind keys for closing this dialog.
37 self.bind('<Return>',self.Ok)
38 self.bind('<Escape>',self.Ok)
Guido van Rossum8ce8a782007-11-01 19:42:39 +000039 self.textView.insert(0.0, text)
Steven M. Gavad721c482001-07-31 10:46:53 +000040 self.textView.config(state=DISABLED)
Terry Jan Reedye91e7632012-02-05 15:14:20 -050041
42 if modal:
43 self.transient(parent)
44 self.grab_set()
45 self.wait_window()
Kurt B. Kaiser6655e4b2002-12-31 16:03:23 +000046
Steven M. Gavad721c482001-07-31 10:46:53 +000047 def CreateWidgets(self):
Kurt B. Kaiser09cb74b2003-06-12 04:20:56 +000048 frameText = Frame(self, relief=SUNKEN, height=700)
Steven M. Gavad721c482001-07-31 10:46:53 +000049 frameButtons = Frame(self)
Kurt B. Kaiser09cb74b2003-06-12 04:20:56 +000050 self.buttonOk = Button(frameButtons, text='Close',
51 command=self.Ok, takefocus=FALSE)
52 self.scrollbarView = Scrollbar(frameText, orient=VERTICAL,
Terry Jan Reedy01e35752016-06-10 18:19:21 -040053 takefocus=FALSE)
Kurt B. Kaiser09cb74b2003-06-12 04:20:56 +000054 self.textView = Text(frameText, wrap=WORD, highlightthickness=0,
55 fg=self.fg, bg=self.bg)
Steven M. Gavad721c482001-07-31 10:46:53 +000056 self.scrollbarView.config(command=self.textView.yview)
57 self.textView.config(yscrollcommand=self.scrollbarView.set)
Kurt B. Kaiser09cb74b2003-06-12 04:20:56 +000058 self.buttonOk.pack()
Steven M. Gavad721c482001-07-31 10:46:53 +000059 self.scrollbarView.pack(side=RIGHT,fill=Y)
60 self.textView.pack(side=LEFT,expand=TRUE,fill=BOTH)
61 frameButtons.pack(side=BOTTOM,fill=X)
62 frameText.pack(side=TOP,expand=TRUE,fill=BOTH)
Kurt B. Kaiser6655e4b2002-12-31 16:03:23 +000063
Steven M. Gavad721c482001-07-31 10:46:53 +000064 def Ok(self, event=None):
65 self.destroy()
Steven M. Gava44d3d1a2001-07-31 06:59:02 +000066
Guido van Rossum8ce8a782007-11-01 19:42:39 +000067
Terry Jan Reedye91e7632012-02-05 15:14:20 -050068def view_text(parent, title, text, modal=True):
69 return TextViewer(parent, title, text, modal)
Guido van Rossum8ce8a782007-11-01 19:42:39 +000070
Terry Jan Reedye91e7632012-02-05 15:14:20 -050071def view_file(parent, title, filename, encoding=None, modal=True):
Guido van Rossum8ce8a782007-11-01 19:42:39 +000072 try:
Éric Araujoccf03a12011-08-01 17:29:36 +020073 with open(filename, 'r', encoding=encoding) as file:
74 contents = file.read()
Terry Jan Reedy82c46152016-06-22 04:54:18 -040075 except OSError:
76 showerror(title='File Load Error',
77 message='Unable to load file %r .' % filename,
78 parent=parent)
79 except UnicodeDecodeError as err:
80 showerror(title='Unicode Decode Error',
81 message=str(err),
82 parent=parent)
Guido van Rossum8ce8a782007-11-01 19:42:39 +000083 else:
Terry Jan Reedye91e7632012-02-05 15:14:20 -050084 return view_text(parent, title, contents, modal)
Guido van Rossum8ce8a782007-11-01 19:42:39 +000085
Steven M. Gava44d3d1a2001-07-31 06:59:02 +000086if __name__ == '__main__':
Terry Jan Reedy537e2c82014-06-05 03:38:34 -040087 import unittest
88 unittest.main('idlelib.idle_test.test_textview', verbosity=2, exit=False)
Terry Jan Reedy1b392ff2014-05-24 18:48:18 -040089 from idlelib.idle_test.htest import run
90 run(TextViewer)