Patch: clearing breakpoints in IDLE

Edward K. Ream edream at tds.net
Tue Mar 5 10:22:51 EST 2002


Hi all:

I am beginning to think that IDLE's debugger suffers from a vicious
cycle:

1. Nobody uses IDLE's debugger, so
2. Nobody complains about its glaring deficiencies, so
3. Nothing gets fixed, so (back to one)

OTOH, it's great fun to be able to hack on IDLE so easily.  Maybe Guido
doesn't want to deprive us all of that fun ;-)

To help break this cycle, I offer the following patch that lets the user
of IDLE clear breakpoints in exactly the same way that they are set,
that is, by right-clicking a source line containing a breakpoint.

(I've inserted backslashes so this doesn't get line-breaked to death.)

1. In PyShell.py, add the following two lines, indicated by # EKR:

    def __init__(self, *args):
        apply(EditorWindow.__init__, (self,) + args)
        self.text.bind("<<set-breakpoint-here>>",\
            self.set_breakpoint_here)
        self.text.bind("<<clear-this-breakpoint>>",\
            self.clear_this_breakpoint) # EKR
        self.text.bind("<<open-python-shell>>", self.flist.open_shell)

    rmenu_specs = [
        ("Set breakpoint here", "<<set-breakpoint-here>>"),
        ("Clear this breakpoint", "<<clear-this-breakpoint>>"), # EKR
    ]

2. In PyShell.py, add the following new method:

    def clear_this_breakpoint(self, event=None):
        if not self.flist.pyshell or \
            not self.flist.pyshell.interp.debugger:
            self.text.bell()
            return
        self.flist.pyshell.interp.debugger.clear_this_breakpoint(self)

3. In Debugger.py, add the following new method:

    def clear_this_breakpoint(self, edit):
        text = edit.text
        filename = edit.io.filename
        if not filename:
            text.bell()
            return
        lineno = int(float(text.index("insert")))
        msg = self.clear_break(filename, lineno)
        if msg:
            text.bell()
            return
        text.tag_remove("BREAK", "insert linestart", \
            "insert lineend+1char")

I believe that's all there is to it.

Aside 1: Unlike the set_breakpoint_here routine, the call to
self.clear_break in clear_this_breakpoint calls the method of the super
class, i.e., the Bcb class.  I don't understand why Debugger.py bothers
to create a set_break method.  Indeed this comment is strange:

# A literal copy of Bdb.set_break() without the print statement at the
end

There is no print statement in Bdb.set_break in v2.1.

Aside 2: In PyShell.py, it seems silly just to ring a bell in
set_breakpoint_here if the debugger hasn't been opened by the user.  How
about opening it for her?  Like this:

    def set_breakpoint_here(self, event=None):
        if not self.flist.pyshell or \
            not self.flist.pyshell.interp.debugger:
            if 1: # EKR: Try to open debugger automatically.
                self.flist.pyshell.toggle_debugger()
                if not self.flist.pyshell or \
                    not self.flist.pyshell.interp.debugger:
                    self.text.bell()
                    return
            else: # old way
                self.text.bell()
        self.flist.pyshell.interp.debugger.set_breakpoint_here(self)

This seems to work for me.

Edward
--------------------------------------------------------------------
Edward K. Ream   email:  edream at tds.net
Leo: Literate Editor with Outlines
Leo: http://personalpages.tds.net/~edream/front.html
--------------------------------------------------------------------



More information about the Python-list mailing list