From 5fe26fb50068243e68a39947d0d6bd7f59af6666 Mon Sep 17 00:00:00 2001 From: Serhiy Storchaka Date: Fri, 19 Jun 2026 00:19:18 +0300 Subject: [PATCH] gh-151674: Add tkinter Text.edit_canundo() and Text.edit_canredo() Wrap the Tk text widget "edit canundo" and "edit canredo" subcommands, which report whether the undo and redo stacks are non-empty. --- Doc/library/tkinter.rst | 14 +++++++++++ Doc/whatsnew/3.16.rst | 8 +++++++ Lib/test/test_tkinter/test_text.py | 23 +++++++++++++++++++ Lib/tkinter/__init__.py | 16 +++++++++++++ ...-06-19-12-00-00.gh-issue-151674.FCYTvs.rst | 3 +++ 5 files changed, 64 insertions(+) create mode 100644 Misc/NEWS.d/next/Library/2026-06-19-12-00-00.gh-issue-151674.FCYTvs.rst diff --git a/Doc/library/tkinter.rst b/Doc/library/tkinter.rst index b0421721bf8d7e5..3d8983c57a12bf0 100644 --- a/Doc/library/tkinter.rst +++ b/Doc/library/tkinter.rst @@ -5475,6 +5475,20 @@ Widget classes inserted or deleted. Otherwise set the flag to the boolean *arg*. + .. method:: edit_canundo() + + Return ``True`` if there is an edit action on the undo stack that can be + undone, and ``False`` otherwise. + + .. versionadded:: next + + .. method:: edit_canredo() + + Return ``True`` if there is an edit action on the redo stack that can be + reapplied, and ``False`` otherwise. + + .. versionadded:: next + .. method:: edit_undo() Undo the most recent edit action, that is, all the inserts and deletes diff --git a/Doc/whatsnew/3.16.rst b/Doc/whatsnew/3.16.rst index 8e4c4a1e9b1de02..1068c585d7f7347 100644 --- a/Doc/whatsnew/3.16.rst +++ b/Doc/whatsnew/3.16.rst @@ -138,6 +138,14 @@ shlex a string, even if it is already safe for a shell without being quoted. (Contributed by Jay Berry in :gh:`148846`.) +tkinter +------- + +* Added new :class:`!tkinter.Text` methods :meth:`~tkinter.Text.edit_canundo` + and :meth:`~tkinter.Text.edit_canredo` which return whether an undo or redo + is possible. + (Contributed by Serhiy Storchaka in :gh:`151674`.) + xml --- diff --git a/Lib/test/test_tkinter/test_text.py b/Lib/test/test_tkinter/test_text.py index 453a4505a0a4da8..188b0dd2a9d549d 100644 --- a/Lib/test/test_tkinter/test_text.py +++ b/Lib/test/test_tkinter/test_text.py @@ -25,6 +25,29 @@ def test_debug(self): text.debug(olddebug) self.assertEqual(text.debug(), olddebug) + def test_edit_undo_redo(self): + text = self.text + text.configure(undo=True) + + self.assertIs(text.edit_canundo(), False) + self.assertIs(text.edit_canredo(), False) + + text.insert('1.0', 'spam') + self.assertIs(text.edit_canundo(), True) + self.assertIs(text.edit_canredo(), False) + + text.edit_undo() + self.assertIs(text.edit_canundo(), False) + self.assertIs(text.edit_canredo(), True) + + text.edit_redo() + self.assertIs(text.edit_canundo(), True) + self.assertIs(text.edit_canredo(), False) + + text.edit_reset() + self.assertIs(text.edit_canundo(), False) + self.assertIs(text.edit_canredo(), False) + def test_search(self): text = self.text diff --git a/Lib/tkinter/__init__.py b/Lib/tkinter/__init__.py index ba8365f56c37a70..559fe87ed46193b 100644 --- a/Lib/tkinter/__init__.py +++ b/Lib/tkinter/__init__.py @@ -3970,6 +3970,22 @@ def edit(self, *args): """ return self.tk.call(self._w, 'edit', *args) + def edit_canredo(self): + """Return whether redo is possible. + + Return True if redo is possible, i.e. when the redo stack is + not empty, and False otherwise. + """ + return self.tk.getboolean(self.edit("canredo")) + + def edit_canundo(self): + """Return whether undo is possible. + + Return True if undo is possible, i.e. when the undo stack is + not empty, and False otherwise. + """ + return self.tk.getboolean(self.edit("canundo")) + def edit_modified(self, arg=None): """Get or Set the modified flag diff --git a/Misc/NEWS.d/next/Library/2026-06-19-12-00-00.gh-issue-151674.FCYTvs.rst b/Misc/NEWS.d/next/Library/2026-06-19-12-00-00.gh-issue-151674.FCYTvs.rst new file mode 100644 index 000000000000000..84e21d4cbc4bd72 --- /dev/null +++ b/Misc/NEWS.d/next/Library/2026-06-19-12-00-00.gh-issue-151674.FCYTvs.rst @@ -0,0 +1,3 @@ +Add the :meth:`~tkinter.Text.edit_canundo` and :meth:`~tkinter.Text.edit_canredo` +methods of :class:`!tkinter.Text`, wrapping the Tk ``edit canundo`` and +``edit canredo`` subcommands.