]> git.saurik.com Git - wxWidgets.git/blobdiff - wxPython/wxPython/lib/ErrorDialogs.py
Added support for current version of "emxomf".
[wxWidgets.git] / wxPython / wxPython / lib / ErrorDialogs.py
index 01d5418d179baddbe4858b933e837f64064b444e..c193980aca4dae20e2af088ba14c83828a5d97b6 100644 (file)
-#!/bin/env python
-#----------------------------------------------------------------------------
-# Name:         ErrorDialogs.py
-# Version:      1.0
-# Created:      September--October 2001
-# Author:       Chris Fama of Wholly Snakes Software,
-#               Chris.Fama@whollysnakes.com
-#----------------------------------------------------------------------------
-"""
-ErrorDialogs.py: by Christopher J. Fama (trading under the name
-Wholly Snakes Software {Australian Business Number: 28379514278}).
-
-This code is released under the auspices of the modified version of
-the GNU Library Public License (LGPL) that constitutes the license
-under which the GUI package wxPython is released [see the file
-LICENSE.TXT accompanying that distribution).  I must also thank Graham
-Boyd, of Boyd Mining, and CEO of the Minserve group of companies
-(www.minserve.com.au), for kindly allowing the release of this
-module under a "free" license, despite a certain part of it's
-development having taken place while working for him...
-
-Please note that this code, written for Python 2.1, is derives from
-code written when Python 1.5.2 was current.  Although since Python 2.0
-the sys.excepthook variable has been available, for ease and potential
-backwards compatibility (or to be more realistic
-backwards-PARTIAL-compatibility!), the code catches errors by
-assigning a custom object to sys.stderr and monitoring calls to it's
-write() method.  Such calls which take place with a new value of
-sys.last_traceback stand as evidence that at interpreter error has
-just occurred; please note that this means that NO OTHER OUTPUT TO
-sys.stderr WILL BE DISPLAYED.  THIS INCLUDES "warnings" generated by
-the interpreter.  As far as I am aware, unless your code itself writes
-to sys.stderr itself, these will be the only things you miss out
-on--and many, if not most or all, of these will occur before your code
-even gets the opportunity to set one of these file-like objects in
-place.  If this is a problem for you and you can't work around it,
-please contact means or the wxPython-users mailing list.
-
-
-DOCUMENTATION:
-
-This is a module to display errors--either explicitly requested by a
-script or arbitrary interpreter errors--these needs arose in the
-course of a commercial (contract) project, but were not developed in
-the course of work on such [well, very little, albeit concurrently]...
-[NBNB.Does not currently support display of other than interpreter errors.]
-
-Usage, after 'from wxPython.lib.ErrorDialogs import *' (all
-identifiers defined in this module begin with "wxPy", and many of them
-with "wxPyError_", so there should be no namespace conflicts...):
-
-    wxPyNewErrorDialog (<win> (['frame='] <frame (can be None)>,
-                                         <OPTIONS>))
-                   ...
-    wxPyDestroyErrorDialogIfPresent () # e.g. when top frame destroyed)
-
-for unhandled errors, or
-
-    returnval = wxpyNonFatalError (<frame (can be None)>,
-                          <HTML message>
-                          [,<OPTIONS>])
-    [NOTE: NOT IMPLEMENTED {IN THIS VERSION} YET...]
-or
-    returnval = wxPyFatalError (<HTML message>,
-                       [,<OPTIONS, an extra one of which may be
-                          'frame=' <frame (defaults to None)>>])
-    [NOTE: NOT IMPLEMENTED {IN THIS VERSION} YET...]
-or
-
-    wxPybNonWindowingError (message)
-
-for explicit errors.
-
-<win> is one of
-    wxPyNonFatalErrorDialog
-    wxPyFatalErrorDialog
-    wxPyFatalErrorDialogWithTraceback
-    wxPyNonFatalErrorDialogWithTraceback
-    wxPyNonWindowingErrorHandler
-
-and the OPTIONS (with defaults) are: (please note that the options for
-wxPyNonWindowingErrorHandler / wxPyNonWindowingError are 'almost' a (small))
-subset of these):
-
-    'modal' [default 1]: block until dismissed.
-
-    'programname' [default "Python program"]: appears inThe
-    caption of the dialog, amidst it's text and (by default) in mailings.
-
-    'whendismissed' option, if given, this should be a string, to be
-    executed in a restricted environment (see rexec module) after
-    dialog dismissal.  Typically, this should be Python code to "clean
-    up" after what was presumably the partial execution of some
-    operation started by the user, after the unexpected interruption
-    by some error [which--at least the way I work, means an unexpected
-    error in the code, since exceptions that may be raised by some
-    foreseen (in a programmatic sense) should normally be handled by
-    try...except clauses].
-    NOTE THAT CURRENTLY THE rexec CODE IS NOT WORKING, SO THIS IS JUST DONE
-    BY exec...
-
-    'mailto': if None, give no "e-mail support" option, otherwise this
-    is meant to be an address for 'bug reports'; a command button will
-    be created for this, which pops up another dialog  [Linux], or a window of
-    another program [Windows].
-
-    On Windows, this will launch your mailer (assuming your mailer
-    would start when a file with the '.eml'extension is double-clicked
-    in Windows Explorer--this will be the case for Microsoft Outlook
-    Express [tm and all those legal necessities] if installed, and the
-    association has not been taken over by some other program.  On
-    Linux, it will open a file dialog to save the message, by default
-    as a '.html' file...{Please note that, on Windows and with current
-    (when I got the machine I'm writing this on--early 2000) versions
-    of Outlook Express, you may need to enter your e-mail address in
-    the box beside the "mail support" button.)
-
-    The template for the mail message is in the 'MessageTemplate'
-    attribute of the dialog-derived class in question (e.g.,
-    wxPyNonFatalErrorDialog).  Search for this in the code below to
-    see the default (note that this template is in HTML format).  This
-    attributes uses the '%{name}s' string conversion feature of Python
-    [see sec.2 of the Python Library Reference]; allowed Lance are:
-    programname version exceptionname exceptionvalue
-    extraexceptioninformation traceback
-
-    'version': str(this) will appear after 'Version' below "Error in
-    <programname>" at the top of the dialog.
-
-EXAMPLES:
-
-    sys.stderr = wxPyNonFatalErrorWindowWithTraceback (
-        parentframe,
-        programname='sumthing',
-        mailto='me@sumwear',
-        whendismissed="from wxPython.wx import * ; wxBell()")
-
-FOR INTERNATIONAL [NON-ENGLISH-SPEAKING] USE:
-    wxPyNonFatalErrorDialog and relatives have the method
-        SetText(Number NUMBER, STRING)
-
-    where STRING is to displayed in the wxStaticText control with ID
-    wxPyError_ID_TEXT<NUMBER>--see the automatically-generated code
-    for information about the meaning of these...
-
-"""
-
-_debug = 0
-#_debug = 1 # uncomment to display some information (to stdout)
-
-from wxPython.wx import *
-import string, sys, traceback, time, rexec, operator, types, tempfile, os
-#from wxPython.lib.createandsendHTMLmail import *# now inline
-import MimeWriter, mimetools, cStringIO, smtplib
-
-from ErrorDialogs_wdr import *
-
-# You may see from the above line that I used the excellent RAD tool
-# wxDesigner, by Robert Roebling, to accelerate development of this
-# module...  The above is left for the convenience of making future
-# changes with wxDesigner; also so the wxDesigner-generated codedoes
-# not need to precede the "hand-generated" code in this file; finally,
-# as a personal endorsement: it is truly a brilliant time-saver!
-# Please note that, at the time of writing, the wxDesigner-generated
-# output requires manual removal of the PythonBitmaps function--an
-# appropriate version of this function will be imported from a
-# similarly- named module.  Another manual change will have to be made
-# to the automatically-generated source: "parent.sizerAroundText = "
-# should be added [immediately] before the text similar to "item13 =
-# wxStaticBoxSizer( item14, wxVERTICAL )", this sizer being the one
-# containing the wxTextCtrl...  [IMPORTANT NOTE: THIS LINE SHOULD BE
-# THE ONE INSTANTIATING A wxStaticBoxSizer, *NOT* THE wxStaticBox
-# ITSELF...]
-
-def wxPyDestroyErrorDialogIfPresent():
-    if isinstance(sys.stderr,wxPyNonFatalErrorDialog):
-        sys.stderr.Destroy()
-    sys.stderr = None
-
-def wxPyNewErrorDialog(dlg):
-    wxPyDestroyErrorDialogIfPresent()
-    sys.stderr = dlg
-
-class wxPyNonWindowingErrorHandler:
-    this_exception = 0
-    softspace = 0
-    def __init__(self,fatal=0,file=sys.__stderr__):
-        self.fatal = fatal
-        self.file = file
-    def write(self,s):
-        import sys
-        if string.find(s,"Warning") <> 0\
-           and  self.this_exception is not sys.last_traceback:
-            wxPyNonWindowingError("The Python interpreter encountered an error "
-                              "not handled by any\nexception handler--this "
-                              "may represent some programming error.",
-                              fatal=self.fatal,
-                               stderr=self.file,
-                              last=1)
-        self.this_exception = sys.last_traceback
-
-def wxPyNonWindowingError(msg,#output=None,errors=None,
-                          stderr=sys.__stderr__,
-                          fatal=1,
-                          last=None):
-    if os.path.exists("wxPyNonWindowingErrors.txt"):
-        mode = 'a+'
-    else:
-        mode = 'w'
-    fl = open("wxPyNonWindowingErrors.txt",mode)
-    if stderr is not None:
-        l = [fl,stderr] # so that the error will be written to the file
-            # before any potential error in stderr.write()... (this is largely
-            # for my own sake in developing...)
-    else:
-        l = [fl]
-    for f in l:
-        f.write(time.ctime (time.time ()) + ": ")
-        f.write(msg)
-        #f.flush()
-        if sys.exc_info () [0] is not None:
-            if last:
-                f.write('Currently handled exception:\n')
-                f.flush()
-            traceback.print_exc(file=f)
-            if last:
-                f.write('\nPrevious (?) error:\n')
-        elif last or sys.last_traceback:
-            f.write("\n\n(For wizards only) ")
-        if last:
-            if type(last) <> types.ListType or len(last) < 3:
-                if (hasattr(sys,"last_traceback") and sys.last_traceback):
-                    last = [sys.last_type ,sys.last_value,sys.last_traceback]
-            if type(last) == types.ListType:
-                traceback.print_exception(last[0],last[1],last[2],
-                                          None,f)
-         #f.flush()
-        if f is sys.__stderr__:
-            s = ' (see the file "wxPyNonWindowingErrors.txt")'
-        else:
-            s = ""
-        f.write("Please contact the author with a copy of this\n"
-                "message%s.\n" % s)
-        #f.flush()
-    fl.close()
-    if fatal and stderr is sys.__stderr__:
-        if sys.platform in ["windows",'nt',"win32"]:
-            sys.__stderr__.write(
-                "\nYou may have to manually close this window to exit.")
-        sys.exit()
-
-class wxPythonRExec (rexec.RExec):
-    def __init__(self,securityhole=0,*args,**kwargs):
-        apply(rexec.RExec.__init__, (self,) + args, kwargs)
-        if securityhole:
-            self.ok_builtin_modules = self.ok_builtin_modules + \
-            ('wxPython', 'wxPython.wxc','wxPython.wx','wxPython.misc',
-             'wxPython.misc2', 'wxPython.windows', 'wxPython.gdi',
-             'wxPython.clip_dnd', 'wxPython.events', 'wxPython.mdi',
-             'wxPython.frames', 'wxPython.stattool', 'wxPython.controls',
-             'wxPython.controls2', 'wxPython.windows2', 'wxPython.cmndlgs',
-             'wxPython.windows3', 'wxPython.image', 'wxPython.printfw',
-             'wxc','misc', 'misc2', 'windows', 'gdi', 'clip_dnd', 'events',
-             'mdi', 'frames', 'stattool', 'controls', 'controls2', 'windows2',
-             'cmndlgs', 'windows3', 'image', 'printfw', 'wx')
-            # possible security hole!
-
-##def wxPyFatalError(msg,frame=None,**kwargs):
-##    kwargs.update({'fatal' : 1})
-##    apply(wxPyNonFatalError,
-##          (frame,msg),
-##          kwargs)
-
-class wxPyNonFatalErrorDialogWithTraceback(wxDialog):
-    this_exception = 0
-    populate_function = populate_wxNonFatalErrorDialogWithTraceback
-    no_continue_button = false
-    fatal = false
-    modal = true
-    exitjustreturns = false # really only for testing!
-
-    def __init__(self, parent, id,
-                 pos = wxPyDefaultPosition, size = wxPyDefaultSize,
-                 style = wxDEFAULT_DIALOG_STYLE,
-                 programname = "Python program",
-                 version = "?",
-                 mailto = None,
-                 whendismissed = "",
-                 disable_exit_button = false):
-
-        if _debug:
-            sys.stdout.write('\nwxPyNonFatalErrorWindow.__init__: '
-                                        'STARTING...\n\n')
-
-        if self.fatal:
-            whetherNF = ""
-        else:
-            whetherNF = "non-"
-        title = "A (%sfatal) error has occurred in %s!"\
-                % (whetherNF,programname)
-        self.programname = programname # save for later use
-        self.mailto = mailto # save for later use
-        self.parent = parent # save for later use
-        self.whendismissed = whendismissed # save for later use
-        self.dialogtitle = title # save for later use
-
-        wxDialog.__init__(self, parent, id, title, pos, size, style)
-
-        self.topsizer = self.populate_function( false,true )
-
-        self.SetProgramName(programname)
-        self.SetVersion(version)
-
-        if not self.no_continue_button:
-            EVT_BUTTON(self, wxPyError_ID_CONTINUE, self.OnContinue)
-        if mailto:
-            disable_mail_button = 0
-        else:
-            disable_mail_button = 1
-        if not disable_mail_button:
-            EVT_BUTTON(self, wxPyError_ID_MAIL, self.OnMail)
-        else:
-            self.GetMailButton().Enable(false)
-        if not disable_exit_button:
-            EVT_BUTTON(self, wxPyError_ID_EXIT, self.OnExit)
-
-        self.nonwindowingerror = wxPyNonWindowingErrorHandler(file=sys.__stderr__,
-                                                              fatal=0)
-
-        if _debug:
-            sys.stdout.write('\nwxPyNonFatalErrorWindow.__init__: '
-                             'DONE.\n\n')
-    def GetExtraInformation(self):
-        return self.extraexceptioninformation
-
-    def SetExtraInformation(self,value):
-        self.extraexceptioninformation = value
-        c = self.GetExtraInformationCtrl()
-        if c is not None:
-            c.SetLabel(str(value))
-            self.topsizer.Layout()
-
-    def GetExtraInformationCtrl(self):
-        return self.FindWindowById(wxPyError_ID_EXTRAINFORMATION)
-
-    def GetExceptionName(self):
-        return str(self.exceptiontype)
-
-    def SetExceptionName(self,value):
-        self.exceptiontype = str(value)
-        c = self.GetExceptionNameCtrl()
-        if c is not None:
-            c.SetLabel(str(value))
-            self.topsizer.Layout()
-
-    def GetExceptionNameCtrl(self):
-        return self.FindWindowById(wxPyError_ID_EXCEPTIONNAME)
-
-    def GetTraceback(self):
-        try:
-            return self.traceback
-        except AttributeError:
-            return None
-
-    def SetTraceback(self,value):
-        self.traceback = value
-        c = self.GetTracebackCtrl()
-        if c is not None:
-            s,cs = c.GetSize(), c.GetClientSize()
-            if value[-1] == '\n':
-                value = value[:-1]
-            if _debug:
-                print "%s.SetTraceback(): ...SetValue('%s' (^M=\\r; ^J=\\n))"\
-                      % (self,string.replace(value,'\n',"^J"))
-            c.SetValue(value)
-
-            # Despite using the wxADJUST_MINSIZE flag in the
-            # appropriate AddWindow method of the sizer, this doesn't
-            # size the control appropriately... evidently the control's
-            # GetBestSize method is not returning the "correct"
-            # value...  So we perform a rather ugly "fix"... note that
-            # this also requires that we remove the wxADJUST_MINSIZE
-            # flag from the AddWindow method of the sizer containing
-            # the wxTextCtrl, which adds the wxTextCtrl...  (this
-            # amounts, as of wxDesigner 2.6, to only a few mouse
-            # clicks...)
-
-            if _debug:
-                size = c.GetBestSize()
-                print "%s.SetTraceback(): %s.GetBestSize() = (%s,%s)"\
-                      % (self,c,size.width,size.height)
-            w,h = 0,0
-            for v in string.split(value,"\n"):
-                pw,ph,d,e = t = c.GetFullTextExtent(v)
-                if _debug:
-                    print v, t
-                h = h + ph + e# + d# + e
-                pw = pw + wxSystemSettings_GetSystemMetric(wxSYS_VSCROLL_X)
-                if pw > w:
-                    w = pw
-            w = w + s.width - cs.width
-            h = h + s.height - cs.height
-            if _debug:
-                print "%s.SetTraceback(): calculated w,h =" % c,\
-                      w,h,"and sys.platform = '%s'" % sys.platform
-            self.sizerAroundText.SetItemMinSize (c,w,h)
-            c.SetSize ((w,h))
-            c.SetSizeHints (w,h,w,h)
-            c.Refresh()#.SetAutoLayout(FALSE)
-
-            #^ the reason we need the above seems to be to replace the
-            #faulty GetBestSize of wxTextCtrl...
-            #self.sizerAroundText.Layout()
-            self.topsizer.Layout()
-
-    def GetTracebackCtrl(self):
-        return self.FindWindowById(wxPyError_ID_TEXTCTRL)
-
-    def GetVersion(self):
-        return self.version
-
-    def SetVersion(self,value):
-        self.version = value
-        c = self.GetVersionNumberCtrl()
-        if c is not None:
-            c.SetLabel(value)
-            self.topsizer.Layout()
-
-    def GetVersionNumberCtrl(self):
-        return self.FindWindowById(wxPyError_ID_VERSIONNUMBER)
-
-    def GetProgramName(self):
-        return self.programname
-
-    def SetProgramName(self,value):
-        self.programname = value
-        c = self.GetProgramNameCtrl()
-        if c is not None:
-            c.SetLabel(value)
-            self.topsizer.Layout()
-
-    def GetProgramNameCtrl(self):
-        return self.FindWindowById(wxPyError_ID_PROGRAMNAME)
-
-    def GetContinueButton(self):
-        return self.FindWindowById(wxPyError_ID_CONTINUE)
-
-    def GetMailButton(self):
-        return self.FindWindowById(wxPyError_ID_MAIL)
-
-    def GetExitButton(self):
-        return self.FindWindowById(wxPyError_ID_EXIT)
-
-    # write handler (which is really the guts of the thing...
-    # [Note that this doesn't use sys.excepthook because I already had a
-    # working body of code...
-
-    def write(self,s):
-        if self.this_exception is not sys.last_traceback:
-          if not wxThread_IsMain():
-              # Aquire the GUI mutex before making GUI calls.  Mutex is released
-              # when locker is deleted at the end of this function.
-              locker = wxMutexGuiLocker()
-
-          self.this_exception = sys.last_traceback
-            # this is meant to be done once per traceback's sys.stderr.write's
-            # - on the first in fact.....
-          try:
-            #from wxPython.wx import wxBell
-            wxBell()
-
-            if _debug:
-                sys.stdout.write(
-                    'in  %s.write(): ' % self)
-
-            self.exceptiontype = sys.last_type
-            self.extraexceptioninformation = sys.last_value
-            c = cStringIO.StringIO()
-            traceback.print_last(None,c)
-            self.traceback = c.getvalue()
-
-            if _debug:
-                #import traceback
-                traceback.print_last(None,sys.stdout)
-
-            self.SetExceptionName(str(self.exceptiontype))
-            self.SetExtraInformation(str(self.extraexceptioninformation))
-            self.SetTraceback(str(self.traceback))
-
-            self.topsizer.Fit(self)
-            self.topsizer.SetSizeHints(self)
-
-            if self.modal:
-                self.ShowModal()
-            else:
-                self.Show(true)
-
-          except:
-              if not locals().has_key("c"):
-                  c = cStringIO.StringIO()
-                  c.write("[Exception occurred before data from "
-                          "sys.last_traceback available]")
-##              c2 = cStringIO.StringIO()
-##              traceback.print_exception(None,c2)
-              wxPyNonWindowingError("Warning: "
-                                "a %s error was encountered trying to "
-                                "handle the exception\n%s\nThis was:"#%s\n"
-                                % (sys.exc_type, c.getvalue()),#, c2.getvalue()),
-                                stderr=sys.__stderr__,
-                                last=0)
-
-
-    # button handlers:
-
-    def OnContinue(self, event):
-     try:
-        if self.whendismissed:
-            parent = self.parent # so whendismissed can refer to "parent"
-            if 1:
-                if _debug:
-                    sys.stdout.write("exec '''%s''': "
-                                         % (self.whendismissed))
-                exec self.whendismissed
-                if _debug: print "\n",
-            else:
-                if _debug:
-                    sys.stdout.write("wxPythonRExec(%s).r_exec('''%s'''): "
-                                         % (self.securityhole,
-                                            self.whendismissed))
-                wxPythonRExec(self.securityhole).r_exec(self.whendismissed)
-                if _debug: print "\n",
-        if self.modal:
-            self.EndModal(wxID_OK)
-        else:
-            self.Close ()
-        if _debug: print "reimporting ",
-        for  m in sys.modules.values():
-            if m and m.__dict__["__name__"][0] in string.uppercase:#hack!
-                if _debug:
-                    print m.__dict__["__name__"],
-                reload (m)
-                if _debug:
-                    print ' ',
-        if _debug:
-            print '\nENDING %s.OnContinue()..\n\n' % (self,),
-     except:
-      wxPyNonWindowingError("Warning: the following exception information"
-                        " may not be the full story.. (because "
-                        "a %s(%s) error was encountered trying to "
-                        "handle the exception)\n\n"
-                        % tuple(sys.exc_info()[:2]),
-                        stderr=sys.__stderr__,
-                        last=0)
-
-    MessageTemplate = "<head>"\
-                 "</head>"\
-                 '<body text="#000000" bgcolor="#FFFFFF">'\
-                 "<p>"\
-                 "<i><b>Hello,</b></i>\n<p>\n"\
-                 '<p><h2><font color="#CC6C00">%(programname)s</font>'\
-                 " error.</h2>\n"\
-                 "I encountered the following error when running your "\
-                 'program <font color="#CC6C00">%(programname)s</font>,'\
-                 "at %(date)s.\n<p>\n"\
-                 "<p>"\
-                 "<h2>Traceback (automatically generated):</h2>\n"\
-                 '<p><font size="-1">\n<pre>%(traceback)s</pre>\n<p></font><p>'\
-                 "\n<p>\n<h2>More information follows:</h2>\n<p>\n"\
-                 '<font color="#CC6C00">'\
-                 '<i>[Insert more '\
-                 "information about the error here, such as what you were "\
-                 "trying to do at the time of the error.  Please "\
-                 "understand that failure to fill in this field will be "\
-                 "interpreted as an invitation to consign this e-mail "\
-                 "straight to the trash can!]\n</i><p>\n"\
-                 "</font><p>\n"\
-                 '<i><b>Yours sincerely,</b></i>\n<p>'\
-                 '<font color="#CC6C00">'\
-                 "[insert your name here]\n"\
-                 "</font>"\
-                 "</body>"
-
-    def OnMail(self,event):
-      try:
-        if _debug:
-            print 'Attempting to write mail message.\n',
-        gmtdate = time.asctime(time.gmtime(time.time())) + ' GMT'
-        tm = time.localtime(time.time())
-        date = time.asctime(tm) + ' ' +\
-               time.strftime("%Z",tm)
-        programname = self.programname
-        traceback = self.traceback
-        mailto = self.mailto
-        message = self.MessageTemplate % vars()
-        subject = "Un-caught exception when running %s." % programname
-        if _debug:
-            print 'message:',message
-            print 'subject:,',subject
-            print 'sent to:',mailto
-        mailfrom = self.FindWindowById (wxPyError_ID_ADDRESS)
-        if mailfrom:
-            mailfrom = mailfrom.GetValue()
-        if _startmailerwithhtml(mailto,subject,message,text="",mailfrom=mailfrom):
-          if not (hasattr(self,"fatal") and self.fatal):
-            self.OnContinue(event) # if ok, then act as if "Continue" selected
-      except:
-              wxPyNonWindowingError("Warning: the following exception information"
-                                " may not be the full story... (because "
-                                "a %s error was encountered trying to "
-                                "handle the original exception)\n\n"#%s"
-                                % (sys.exc_type,),#self.msg),
-                                stderr=sys.__stderr__,
-                                last=0)
-
-    def OnExit(self, event):
-        if self.IsModal():
-            self.EndModal(wxID_CANCEL)
-        if self.exitjustreturns:
-            return
-        wxGetApp().ExitMainLoop()
-
-##         if isinstance(sys.stderr,wxPyNonFatalErrorDialogWithTraceback):
-##             if sys.stderr == self:
-##                 selfdestroyed = 1
-##             sys.stderr.Destroy()
-##         sys.stderr = wxPyNonWindowingErrorHandler(sys.__stderr__)
-##         wxSafeYield() # so remaining events are processed...
-##         if self.parent not in [None,NULL]:
-##             self.parent.Destroy()
-##         elif "selfdestroyed" not  in locals().keys():
-##             self.Destroy()
-
-    def SetText(self,number,string):
-        self.FindWindowById(eval("wxPyError_ID_TEXT%d"
-                                 % number)).SetLabel(string)
-        self.topsizer.Layout()
-
-class wxPyFatalErrorDialogWithTraceback(wxPyNonFatalErrorDialogWithTraceback):
-    populate_function = populate_wxFatalErrorDialogWithTraceback
-    no_continue_button = true
-    fatal = true
-
-class wxPyNonFatalErrorDialog(wxPyNonFatalErrorDialogWithTraceback):
-    populate_function = populate_wxNonFatalErrorDialog
-
-class wxPyFatalErrorDialog(wxPyFatalErrorDialogWithTraceback):
-    populate_function = populate_wxFatalErrorDialog
-
-
-def _startmailerwithhtml(mailto,subject,html,text,mailfrom=None):
-    if sys.platform in ["windows",'nt',"win32"] and sys.hexversion >= 0x02000000:
-        name = tempfile.mktemp(".eml")
-        f = open(name,"w")
-        f.write(_createhtmlmail(html,text,subject,to=mailto,
-                               mailfrom=mailfrom))
-        f.close()
-        try:
-            os.startfile(name)
-        except WindowsError:
-            # probably no association with eml files
-            return _writehtmlmessage(mailto,subject,html,text,mailfrom=mailfrom)
-        return 1
-    else:
-        return _writehtmlmessage(mailto,subject,html,text,mailfrom=mailfrom)
-
-def _writehtmlmessage(mailto,subject,html,text=None,parent=None,mailfrom=None):
-    dlg = wxFileDialog (parent,
-                        "Please choose a a file to save the message to...",
-                        ".",
-                        "bug-report",
-                        "HTML files (*.htm,*.html)|*.htm,*.html|"
-                        "All files (*)|*",
-                        wxSAVE | wxHIDE_READONLY)
-    if dlg.ShowModal() <> wxID_CANCEL:
-        f = open(dlg.GetPath(),"w")
-        dlg.Destroy()
-        f.write(_createhtmlmail(html,text,subject,to=mailto,mailfrom=mailfrom))
-        f.close()
-        return 1
-    else:
-        return 0
-
-# PLEASE NOTE THAT THE CODE BELOW FOR STARTING MAILER WITH A GIVEN
-#(HTML) MESSAGE IS BY ART GILLESPIE [with slight modifications by yours truly].
-
-def _createhtmlmail (html, text, subject, to=None, mailfrom=None):
-    """Create a mime-message that will render HTML in popular
-       MUAs, text in better ones (if indeed text is not untrue (e.g. None)
-       """
-    # imported above #import MimeWriter, mimetools, cStringIO
-
-    out = cStringIO.StringIO() # output buffer for our message
-    htmlin = cStringIO.StringIO(html)
-    if text:
-            txtin = cStringIO.StringIO(text)
-
-    writer = MimeWriter.MimeWriter(out)
-    #
-    # set up some basic headers... we put subject here
-    # because smtplib.sendmail expects it to be in the
-    # message body
-    #
-    if mailfrom:
-            writer.addheader("From", mailfrom)
-            #writer.addheader("Reply-to", mailfrom)
-    writer.addheader("Subject", subject)
-    if to:
-            writer.addheader("To", to)
-    writer.addheader("MIME-Version", "1.0")
-    #
-    # start the multipart section of the message
-    # multipart/alternative seems to work better
-    # on some MUAs than multipart/mixed
-    #
-    writer.startmultipartbody("alternative")
-    writer.flushheaders()
-    #
-    # the plain text section
-    #
-    if text:
-        subpart = writer.nextpart()
-        subpart.addheader("Content-Transfer-Encoding", "quoted-printable")
-        pout = subpart.startbody("text/plain", [("charset", 'us-ascii')])
-        mimetools.encode(txtin, pout, 'quoted-printable')
-        txtin.close()
-    #
-    # start the html subpart of the message
-    #
-    subpart = writer.nextpart()
-    subpart.addheader("Content-Transfer-Encoding", "quoted-printable")
-    pout = subpart.startbody("text/html", [("charset", 'us-ascii')])
-    mimetools.encode(htmlin, pout, 'quoted-printable')
-    htmlin.close()
-    #
-    # Now that we're done, close our writer and
-    # return the message body
-    #
-    writer.lastpart()
-    msg = out.getvalue()
-    out.close()
-    return msg
-
-def _sendmail(mailto,subject,html,text):# currently unused
-    """For illustration only--this function is not actually used."""
-    message = _createhtmlmail(html, text, subject)
-    server = smtplib.SMTP("localhost")
-    server.sendmail(mailto, subject, message)
-    server.quit()
+## This file imports items from the wx package into the wxPython package for
+## backwards compatibility.  Some names will also have a 'wx' added on if
+## that is how they used to be named in the old wxPython package.
+
+import wx.lib.ErrorDialogs
+
+__doc__ =  wx.lib.ErrorDialogs.__doc__
+
+_createhtmlmail = wx.lib.ErrorDialogs._createhtmlmail
+_sendmail = wx.lib.ErrorDialogs._sendmail
+_startmailerwithhtml = wx.lib.ErrorDialogs._startmailerwithhtml
+_writehtmlmessage = wx.lib.ErrorDialogs._writehtmlmessage
+wxPyDestroyErrorDialogIfPresent = wx.lib.ErrorDialogs.wxPyDestroyErrorDialogIfPresent
+wxPyFatalError = wx.lib.ErrorDialogs.wxPyFatalError
+wxPyFatalErrorDialog = wx.lib.ErrorDialogs.wxPyFatalErrorDialog
+wxPyFatalErrorDialogWithTraceback = wx.lib.ErrorDialogs.wxPyFatalErrorDialogWithTraceback
+wxPyFatalOrNonFatalError = wx.lib.ErrorDialogs.wxPyFatalOrNonFatalError
+wxPyNewErrorDialog = wx.lib.ErrorDialogs.wxPyNewErrorDialog
+wxPyNonFatalError = wx.lib.ErrorDialogs.wxPyNonFatalError
+wxPyNonFatalErrorDialog = wx.lib.ErrorDialogs.wxPyNonFatalErrorDialog
+wxPyNonFatalErrorDialogWithTraceback = wx.lib.ErrorDialogs.wxPyNonFatalErrorDialogWithTraceback
+wxPyNonWindowingError = wx.lib.ErrorDialogs.wxPyNonWindowingError
+wxPyNonWindowingErrorHandler = wx.lib.ErrorDialogs.wxPyNonWindowingErrorHandler
+wxPyResizeHTMLWindowToDispelScrollbar = wx.lib.ErrorDialogs.wxPyResizeHTMLWindowToDispelScrollbar
+wxPythonRExec = wx.lib.ErrorDialogs.wxPythonRExec