plugins/python/PythonEditor.py
changeset 657 340c0b9caeca
parent 654 9f6c091c316c
child 670 fb03cb6da95c
equal deleted inserted replaced
656:c1792dfc8c7e 657:340c0b9caeca
     1 import  wx, wx.grid
     1 import  wx, wx.grid
     2 import  wx.stc  as  stc
     2 import  wx.stc  as  stc
     3 import keyword
     3 import keyword
       
     4 
       
     5 from controls import EditorPanel
     4 
     6 
     5 if wx.Platform == '__WXMSW__':
     7 if wx.Platform == '__WXMSW__':
     6     faces = { 'times': 'Times New Roman',
     8     faces = { 'times': 'Times New Roman',
     7               'mono' : 'Courier New',
     9               'mono' : 'Courier New',
     8               'helv' : 'Arial',
    10               'helv' : 'Arial',
    25               'other': 'new century schoolbook',
    27               'other': 'new century schoolbook',
    26               'size' : 12,
    28               'size' : 12,
    27               'size2': 10,
    29               'size2': 10,
    28              }
    30              }
    29 
    31 
    30 def AppendMenu(parent, help, id, kind, text):
       
    31     if wx.VERSION >= (2, 6, 0):
       
    32         parent.Append(help=help, id=id, kind=kind, text=text)
       
    33     else:
       
    34         parent.Append(helpString=help, id=id, kind=kind, item=text)
       
    35 
       
    36 
       
    37 [ID_PYTHONEDITOR,
    32 [ID_PYTHONEDITOR,
    38 ] = [wx.NewId() for _init_ctrls in range(1)]
    33 ] = [wx.NewId() for _init_ctrls in range(1)]
    39 
    34 
    40 def GetCursorPos(old, new):
    35 def GetCursorPos(old, new):
    41     old_length = len(old)
    36     old_length = len(old)
    56         else:
    51         else:
    57             return i + 1
    52             return i + 1
    58     else:
    53     else:
    59         return None
    54         return None
    60 
    55 
    61 class PythonEditor(stc.StyledTextCtrl):
    56 class PythonEditor(EditorPanel):
    62 
    57 
    63     fold_symbols = 3
    58     fold_symbols = 3
    64     
    59     
    65     def __init__(self, parent, window, controler):
    60     def _init_Editor(self, prnt):
    66         stc.StyledTextCtrl.__init__(self, parent, ID_PYTHONEDITOR, wx.DefaultPosition, 
    61         self.Editor = stc.StyledTextCtrl(id=ID_PYTHONEDITOR, parent=prnt,
    67                  wx.DefaultSize, 0)
    62                  name="TextViewer", pos=wx.DefaultPosition, 
    68 
    63                  size=wx.DefaultSize, style=0)
    69         self.CmdKeyAssign(ord('B'), stc.STC_SCMOD_CTRL, stc.STC_CMD_ZOOMIN)
    64 
    70         self.CmdKeyAssign(ord('N'), stc.STC_SCMOD_CTRL, stc.STC_CMD_ZOOMOUT)
    65         self.Editor.CmdKeyAssign(ord('B'), stc.STC_SCMOD_CTRL, stc.STC_CMD_ZOOMIN)
    71 
    66         self.Editor.CmdKeyAssign(ord('N'), stc.STC_SCMOD_CTRL, stc.STC_CMD_ZOOMOUT)
    72         self.SetLexer(stc.STC_LEX_PYTHON)
    67 
    73         self.SetKeyWords(0, " ".join(keyword.kwlist))
    68         self.Editor.SetLexer(stc.STC_LEX_PYTHON)
    74 
    69         self.Editor.SetKeyWords(0, " ".join(keyword.kwlist))
    75         self.SetProperty("fold", "1")
    70 
    76         self.SetProperty("tab.timmy.whinge.level", "1")
    71         self.Editor.SetProperty("fold", "1")
    77         self.SetMargins(0,0)
    72         self.Editor.SetProperty("tab.timmy.whinge.level", "1")
    78 
    73         self.Editor.SetMargins(0,0)
    79         self.SetViewWhiteSpace(False)
    74 
    80         #self.SetBufferedDraw(False)
    75         self.Editor.SetViewWhiteSpace(False)
    81         #self.SetViewEOL(True)
    76         
    82         #self.SetEOLMode(stc.STC_EOL_CRLF)
    77         self.Editor.SetEdgeMode(stc.STC_EDGE_BACKGROUND)
    83         #self.SetUseAntiAliasing(True)
    78         self.Editor.SetEdgeColumn(78)
    84         
       
    85         self.SetEdgeMode(stc.STC_EDGE_BACKGROUND)
       
    86         self.SetEdgeColumn(78)
       
    87 
    79 
    88         # Set up the numbers in the margin for margin #1
    80         # Set up the numbers in the margin for margin #1
    89         self.SetMarginType(1, wx.stc.STC_MARGIN_NUMBER)
    81         self.Editor.SetMarginType(1, wx.stc.STC_MARGIN_NUMBER)
    90         # Reasonable value for, say, 4-5 digits using a mono font (40 pix)
    82         # Reasonable value for, say, 4-5 digits using a mono font (40 pix)
    91         self.SetMarginWidth(1, 40)
    83         self.Editor.SetMarginWidth(1, 40)
    92 
    84 
    93         # Setup a margin to hold fold markers
    85         # Setup a margin to hold fold markers
    94         self.SetMarginType(2, stc.STC_MARGIN_SYMBOL)
    86         self.Editor.SetMarginType(2, stc.STC_MARGIN_SYMBOL)
    95         self.SetMarginMask(2, stc.STC_MASK_FOLDERS)
    87         self.Editor.SetMarginMask(2, stc.STC_MASK_FOLDERS)
    96         self.SetMarginSensitive(2, True)
    88         self.Editor.SetMarginSensitive(2, True)
    97         self.SetMarginWidth(2, 12)
    89         self.Editor.SetMarginWidth(2, 12)
    98 
    90 
    99         if self.fold_symbols == 0:
    91         if self.fold_symbols == 0:
   100             # Arrow pointing right for contracted folders, arrow pointing down for expanded
    92             # Arrow pointing right for contracted folders, arrow pointing down for expanded
   101             self.MarkerDefine(stc.STC_MARKNUM_FOLDEROPEN,    stc.STC_MARK_ARROWDOWN, "black", "black")
    93             self.Editor.MarkerDefine(stc.STC_MARKNUM_FOLDEROPEN,    stc.STC_MARK_ARROWDOWN, "black", "black")
   102             self.MarkerDefine(stc.STC_MARKNUM_FOLDER,        stc.STC_MARK_ARROW, "black", "black")
    94             self.Editor.MarkerDefine(stc.STC_MARKNUM_FOLDER,        stc.STC_MARK_ARROW, "black", "black")
   103             self.MarkerDefine(stc.STC_MARKNUM_FOLDERSUB,     stc.STC_MARK_EMPTY, "black", "black")
    95             self.Editor.MarkerDefine(stc.STC_MARKNUM_FOLDERSUB,     stc.STC_MARK_EMPTY, "black", "black")
   104             self.MarkerDefine(stc.STC_MARKNUM_FOLDERTAIL,    stc.STC_MARK_EMPTY, "black", "black")
    96             self.Editor.MarkerDefine(stc.STC_MARKNUM_FOLDERTAIL,    stc.STC_MARK_EMPTY, "black", "black")
   105             self.MarkerDefine(stc.STC_MARKNUM_FOLDEREND,     stc.STC_MARK_EMPTY,     "white", "black")
    97             self.Editor.MarkerDefine(stc.STC_MARKNUM_FOLDEREND,     stc.STC_MARK_EMPTY,     "white", "black")
   106             self.MarkerDefine(stc.STC_MARKNUM_FOLDEROPENMID, stc.STC_MARK_EMPTY,     "white", "black")
    98             self.Editor.MarkerDefine(stc.STC_MARKNUM_FOLDEROPENMID, stc.STC_MARK_EMPTY,     "white", "black")
   107             self.MarkerDefine(stc.STC_MARKNUM_FOLDERMIDTAIL, stc.STC_MARK_EMPTY,     "white", "black")
    99             self.Editor.MarkerDefine(stc.STC_MARKNUM_FOLDERMIDTAIL, stc.STC_MARK_EMPTY,     "white", "black")
   108             
   100             
   109         elif self.fold_symbols == 1:
   101         elif self.fold_symbols == 1:
   110             # Plus for contracted folders, minus for expanded
   102             # Plus for contracted folders, minus for expanded
   111             self.MarkerDefine(stc.STC_MARKNUM_FOLDEROPEN,    stc.STC_MARK_MINUS, "white", "black")
   103             self.Editor.MarkerDefine(stc.STC_MARKNUM_FOLDEROPEN,    stc.STC_MARK_MINUS, "white", "black")
   112             self.MarkerDefine(stc.STC_MARKNUM_FOLDER,        stc.STC_MARK_PLUS,  "white", "black")
   104             self.Editor.MarkerDefine(stc.STC_MARKNUM_FOLDER,        stc.STC_MARK_PLUS,  "white", "black")
   113             self.MarkerDefine(stc.STC_MARKNUM_FOLDERSUB,     stc.STC_MARK_EMPTY, "white", "black")
   105             self.Editor.MarkerDefine(stc.STC_MARKNUM_FOLDERSUB,     stc.STC_MARK_EMPTY, "white", "black")
   114             self.MarkerDefine(stc.STC_MARKNUM_FOLDERTAIL,    stc.STC_MARK_EMPTY, "white", "black")
   106             self.Editor.MarkerDefine(stc.STC_MARKNUM_FOLDERTAIL,    stc.STC_MARK_EMPTY, "white", "black")
   115             self.MarkerDefine(stc.STC_MARKNUM_FOLDEREND,     stc.STC_MARK_EMPTY, "white", "black")
   107             self.Editor.MarkerDefine(stc.STC_MARKNUM_FOLDEREND,     stc.STC_MARK_EMPTY, "white", "black")
   116             self.MarkerDefine(stc.STC_MARKNUM_FOLDEROPENMID, stc.STC_MARK_EMPTY, "white", "black")
   108             self.Editor.MarkerDefine(stc.STC_MARKNUM_FOLDEROPENMID, stc.STC_MARK_EMPTY, "white", "black")
   117             self.MarkerDefine(stc.STC_MARKNUM_FOLDERMIDTAIL, stc.STC_MARK_EMPTY, "white", "black")
   109             self.Editor.MarkerDefine(stc.STC_MARKNUM_FOLDERMIDTAIL, stc.STC_MARK_EMPTY, "white", "black")
   118 
   110 
   119         elif self.fold_symbols == 2:
   111         elif self.fold_symbols == 2:
   120             # Like a flattened tree control using circular headers and curved joins
   112             # Like a flattened tree control using circular headers and curved joins
   121             self.MarkerDefine(stc.STC_MARKNUM_FOLDEROPEN,    stc.STC_MARK_CIRCLEMINUS,          "white", "#404040")
   113             self.Editor.MarkerDefine(stc.STC_MARKNUM_FOLDEROPEN,    stc.STC_MARK_CIRCLEMINUS,          "white", "#404040")
   122             self.MarkerDefine(stc.STC_MARKNUM_FOLDER,        stc.STC_MARK_CIRCLEPLUS,           "white", "#404040")
   114             self.Editor.MarkerDefine(stc.STC_MARKNUM_FOLDER,        stc.STC_MARK_CIRCLEPLUS,           "white", "#404040")
   123             self.MarkerDefine(stc.STC_MARKNUM_FOLDERSUB,     stc.STC_MARK_VLINE,                "white", "#404040")
   115             self.Editor.MarkerDefine(stc.STC_MARKNUM_FOLDERSUB,     stc.STC_MARK_VLINE,                "white", "#404040")
   124             self.MarkerDefine(stc.STC_MARKNUM_FOLDERTAIL,    stc.STC_MARK_LCORNERCURVE,         "white", "#404040")
   116             self.Editor.MarkerDefine(stc.STC_MARKNUM_FOLDERTAIL,    stc.STC_MARK_LCORNERCURVE,         "white", "#404040")
   125             self.MarkerDefine(stc.STC_MARKNUM_FOLDEREND,     stc.STC_MARK_CIRCLEPLUSCONNECTED,  "white", "#404040")
   117             self.Editor.MarkerDefine(stc.STC_MARKNUM_FOLDEREND,     stc.STC_MARK_CIRCLEPLUSCONNECTED,  "white", "#404040")
   126             self.MarkerDefine(stc.STC_MARKNUM_FOLDEROPENMID, stc.STC_MARK_CIRCLEMINUSCONNECTED, "white", "#404040")
   118             self.Editor.MarkerDefine(stc.STC_MARKNUM_FOLDEROPENMID, stc.STC_MARK_CIRCLEMINUSCONNECTED, "white", "#404040")
   127             self.MarkerDefine(stc.STC_MARKNUM_FOLDERMIDTAIL, stc.STC_MARK_TCORNERCURVE,         "white", "#404040")
   119             self.Editor.MarkerDefine(stc.STC_MARKNUM_FOLDERMIDTAIL, stc.STC_MARK_TCORNERCURVE,         "white", "#404040")
   128 
   120 
   129         elif self.fold_symbols == 3:
   121         elif self.fold_symbols == 3:
   130             # Like a flattened tree control using square headers
   122             # Like a flattened tree control using square headers
   131             self.MarkerDefine(stc.STC_MARKNUM_FOLDEROPEN,    stc.STC_MARK_BOXMINUS,          "white", "#808080")
   123             self.Editor.MarkerDefine(stc.STC_MARKNUM_FOLDEROPEN,    stc.STC_MARK_BOXMINUS,          "white", "#808080")
   132             self.MarkerDefine(stc.STC_MARKNUM_FOLDER,        stc.STC_MARK_BOXPLUS,           "white", "#808080")
   124             self.Editor.MarkerDefine(stc.STC_MARKNUM_FOLDER,        stc.STC_MARK_BOXPLUS,           "white", "#808080")
   133             self.MarkerDefine(stc.STC_MARKNUM_FOLDERSUB,     stc.STC_MARK_VLINE,             "white", "#808080")
   125             self.Editor.MarkerDefine(stc.STC_MARKNUM_FOLDERSUB,     stc.STC_MARK_VLINE,             "white", "#808080")
   134             self.MarkerDefine(stc.STC_MARKNUM_FOLDERTAIL,    stc.STC_MARK_LCORNER,           "white", "#808080")
   126             self.Editor.MarkerDefine(stc.STC_MARKNUM_FOLDERTAIL,    stc.STC_MARK_LCORNER,           "white", "#808080")
   135             self.MarkerDefine(stc.STC_MARKNUM_FOLDEREND,     stc.STC_MARK_BOXPLUSCONNECTED,  "white", "#808080")
   127             self.Editor.MarkerDefine(stc.STC_MARKNUM_FOLDEREND,     stc.STC_MARK_BOXPLUSCONNECTED,  "white", "#808080")
   136             self.MarkerDefine(stc.STC_MARKNUM_FOLDEROPENMID, stc.STC_MARK_BOXMINUSCONNECTED, "white", "#808080")
   128             self.Editor.MarkerDefine(stc.STC_MARKNUM_FOLDEROPENMID, stc.STC_MARK_BOXMINUSCONNECTED, "white", "#808080")
   137             self.MarkerDefine(stc.STC_MARKNUM_FOLDERMIDTAIL, stc.STC_MARK_TCORNER,           "white", "#808080")
   129             self.Editor.MarkerDefine(stc.STC_MARKNUM_FOLDERMIDTAIL, stc.STC_MARK_TCORNER,           "white", "#808080")
   138 
   130 
   139 
   131 
   140         self.Bind(stc.EVT_STC_UPDATEUI, self.OnUpdateUI)
   132         self.Editor.Bind(stc.EVT_STC_UPDATEUI, self.OnUpdateUI)
   141         self.Bind(stc.EVT_STC_MARGINCLICK, self.OnMarginClick)
   133         self.Editor.Bind(stc.EVT_STC_MARGINCLICK, self.OnMarginClick)
   142         self.Bind(wx.EVT_KEY_DOWN, self.OnKeyPressed)
   134         self.Editor.Bind(wx.EVT_KEY_DOWN, self.OnKeyPressed)
   143 
   135 
   144         # Global default style
   136         # Global default style
   145         if wx.Platform == '__WXMSW__':
   137         if wx.Platform == '__WXMSW__':
   146             self.StyleSetSpec(stc.STC_STYLE_DEFAULT, 
   138             self.Editor.StyleSetSpec(stc.STC_STYLE_DEFAULT, 'fore:#000000,back:#FFFFFF,face:Courier New')
   147                               'fore:#000000,back:#FFFFFF,face:Courier New')
       
   148         elif wx.Platform == '__WXMAC__':
   139         elif wx.Platform == '__WXMAC__':
   149             # TODO: if this looks fine on Linux too, remove the Mac-specific case 
   140             # TODO: if this looks fine on Linux too, remove the Mac-specific case 
   150             # and use this whenever OS != MSW.
   141             # and use this whenever OS != MSW.
   151             self.StyleSetSpec(stc.STC_STYLE_DEFAULT, 
   142             self.Editor.StyleSetSpec(stc.STC_STYLE_DEFAULT, 'fore:#000000,back:#FFFFFF,face:Monaco')
   152                               'fore:#000000,back:#FFFFFF,face:Monaco')
       
   153         else:
   143         else:
   154             defsize = wx.SystemSettings.GetFont(wx.SYS_ANSI_FIXED_FONT).GetPointSize()
   144             defsize = wx.SystemSettings.GetFont(wx.SYS_ANSI_FIXED_FONT).GetPointSize()
   155             self.StyleSetSpec(stc.STC_STYLE_DEFAULT, 
   145             self.Editor.StyleSetSpec(stc.STC_STYLE_DEFAULT, 'fore:#000000,back:#FFFFFF,face:Courier,size:%d'%defsize)
   156                               'fore:#000000,back:#FFFFFF,face:Courier,size:%d'%defsize)
       
   157 
   146 
   158         # Clear styles and revert to default.
   147         # Clear styles and revert to default.
   159         self.StyleClearAll()
   148         self.Editor.StyleClearAll()
   160 
   149 
   161         # Following style specs only indicate differences from default.
   150         # Following style specs only indicate differences from default.
   162         # The rest remains unchanged.
   151         # The rest remains unchanged.
   163 
   152 
   164         # Line numbers in margin
   153         # Line numbers in margin
   165         self.StyleSetSpec(wx.stc.STC_STYLE_LINENUMBER,'fore:#000000,back:#99A9C2')    
   154         self.Editor.StyleSetSpec(wx.stc.STC_STYLE_LINENUMBER,'fore:#000000,back:#99A9C2')    
   166         # Highlighted brace
   155         # Highlighted brace
   167         self.StyleSetSpec(wx.stc.STC_STYLE_BRACELIGHT,'fore:#00009D,back:#FFFF00')
   156         self.Editor.StyleSetSpec(wx.stc.STC_STYLE_BRACELIGHT,'fore:#00009D,back:#FFFF00')
   168         # Unmatched brace
   157         # Unmatched brace
   169         self.StyleSetSpec(wx.stc.STC_STYLE_BRACEBAD,'fore:#00009D,back:#FF0000')
   158         self.Editor.StyleSetSpec(wx.stc.STC_STYLE_BRACEBAD,'fore:#00009D,back:#FF0000')
   170         # Indentation guide
   159         # Indentation guide
   171         self.StyleSetSpec(wx.stc.STC_STYLE_INDENTGUIDE, "fore:#CDCDCD")
   160         self.Editor.StyleSetSpec(wx.stc.STC_STYLE_INDENTGUIDE, "fore:#CDCDCD")
   172 
   161 
   173         # Python styles
   162         # Python styles
   174         self.StyleSetSpec(wx.stc.STC_P_DEFAULT, 'fore:#000000')
   163         self.Editor.StyleSetSpec(wx.stc.STC_P_DEFAULT, 'fore:#000000')
   175         # Comments
   164         # Comments
   176         self.StyleSetSpec(wx.stc.STC_P_COMMENTLINE,  'fore:#008000,back:#F0FFF0')
   165         self.Editor.StyleSetSpec(wx.stc.STC_P_COMMENTLINE,  'fore:#008000,back:#F0FFF0')
   177         self.StyleSetSpec(wx.stc.STC_P_COMMENTBLOCK, 'fore:#008000,back:#F0FFF0')
   166         self.Editor.StyleSetSpec(wx.stc.STC_P_COMMENTBLOCK, 'fore:#008000,back:#F0FFF0')
   178         # Numbers
   167         # Numbers
   179         self.StyleSetSpec(wx.stc.STC_P_NUMBER, 'fore:#008080')
   168         self.Editor.StyleSetSpec(wx.stc.STC_P_NUMBER, 'fore:#008080')
   180         # Strings and characters
   169         # Strings and characters
   181         self.StyleSetSpec(wx.stc.STC_P_STRING, 'fore:#800080')
   170         self.Editor.StyleSetSpec(wx.stc.STC_P_STRING, 'fore:#800080')
   182         self.StyleSetSpec(wx.stc.STC_P_CHARACTER, 'fore:#800080')
   171         self.Editor.StyleSetSpec(wx.stc.STC_P_CHARACTER, 'fore:#800080')
   183         # Keywords
   172         # Keywords
   184         self.StyleSetSpec(wx.stc.STC_P_WORD, 'fore:#000080,bold')
   173         self.Editor.StyleSetSpec(wx.stc.STC_P_WORD, 'fore:#000080,bold')
   185         # Triple quotes
   174         # Triple quotes
   186         self.StyleSetSpec(wx.stc.STC_P_TRIPLE, 'fore:#800080,back:#FFFFEA')
   175         self.Editor.StyleSetSpec(wx.stc.STC_P_TRIPLE, 'fore:#800080,back:#FFFFEA')
   187         self.StyleSetSpec(wx.stc.STC_P_TRIPLEDOUBLE, 'fore:#800080,back:#FFFFEA')
   176         self.Editor.StyleSetSpec(wx.stc.STC_P_TRIPLEDOUBLE, 'fore:#800080,back:#FFFFEA')
   188         # Class names
   177         # Class names
   189         self.StyleSetSpec(wx.stc.STC_P_CLASSNAME, 'fore:#0000FF,bold')
   178         self.Editor.StyleSetSpec(wx.stc.STC_P_CLASSNAME, 'fore:#0000FF,bold')
   190         # Function names
   179         # Function names
   191         self.StyleSetSpec(wx.stc.STC_P_DEFNAME, 'fore:#008080,bold')
   180         self.Editor.StyleSetSpec(wx.stc.STC_P_DEFNAME, 'fore:#008080,bold')
   192         # Operators
   181         # Operators
   193         self.StyleSetSpec(wx.stc.STC_P_OPERATOR, 'fore:#800000,bold')
   182         self.Editor.StyleSetSpec(wx.stc.STC_P_OPERATOR, 'fore:#800000,bold')
   194         # Identifiers. I leave this as not bold because everything seems
   183         # Identifiers. I leave this as not bold because everything seems
   195         # to be an identifier if it doesn't match the above criterae
   184         # to be an identifier if it doesn't match the above criterae
   196         self.StyleSetSpec(wx.stc.STC_P_IDENTIFIER, 'fore:#000000')
   185         self.Editor.StyleSetSpec(wx.stc.STC_P_IDENTIFIER, 'fore:#000000')
   197 
   186 
   198         # Caret color
   187         # Caret color
   199         self.SetCaretForeground("BLUE")
   188         self.Editor.SetCaretForeground("BLUE")
   200         # Selection background
   189         # Selection background
   201         self.SetSelBackground(1, '#66CCFF')
   190         self.Editor.SetSelBackground(1, '#66CCFF')
   202 
   191 
   203         self.SetSelBackground(True, wx.SystemSettings_GetColour(wx.SYS_COLOUR_HIGHLIGHT))
   192         self.Editor.SetSelBackground(True, wx.SystemSettings_GetColour(wx.SYS_COLOUR_HIGHLIGHT))
   204         self.SetSelForeground(True, wx.SystemSettings_GetColour(wx.SYS_COLOUR_HIGHLIGHTTEXT))
   193         self.Editor.SetSelForeground(True, wx.SystemSettings_GetColour(wx.SYS_COLOUR_HIGHLIGHTTEXT))
   205         
   194         
   206         # register some images for use in the AutoComplete box.
   195         # register some images for use in the AutoComplete box.
   207         #self.RegisterImage(1, images.getSmilesBitmap())
   196         #self.RegisterImage(1, images.getSmilesBitmap())
   208         self.RegisterImage(1, 
   197         self.Editor.RegisterImage(1, 
   209             wx.ArtProvider.GetBitmap(wx.ART_DELETE, size=(16,16)))
   198             wx.ArtProvider.GetBitmap(wx.ART_DELETE, size=(16,16)))
   210         self.RegisterImage(2, 
   199         self.Editor.RegisterImage(2, 
   211             wx.ArtProvider.GetBitmap(wx.ART_NEW, size=(16,16)))
   200             wx.ArtProvider.GetBitmap(wx.ART_NEW, size=(16,16)))
   212         self.RegisterImage(3, 
   201         self.Editor.RegisterImage(3, 
   213             wx.ArtProvider.GetBitmap(wx.ART_COPY, size=(16,16)))
   202             wx.ArtProvider.GetBitmap(wx.ART_COPY, size=(16,16)))
   214 
   203 
   215         # Indentation and tab stuff
   204         # Indentation and tab stuff
   216         self.SetIndent(4)               # Proscribed indent size for wx
   205         self.Editor.SetIndent(4)               # Proscribed indent size for wx
   217         self.SetIndentationGuides(True) # Show indent guides
   206         self.Editor.SetIndentationGuides(True) # Show indent guides
   218         self.SetBackSpaceUnIndents(True)# Backspace unindents rather than delete 1 space
   207         self.Editor.SetBackSpaceUnIndents(True)# Backspace unindents rather than delete 1 space
   219         self.SetTabIndents(True)        # Tab key indents
   208         self.Editor.SetTabIndents(True)        # Tab key indents
   220         self.SetTabWidth(4)             # Proscribed tab size for wx
   209         self.Editor.SetTabWidth(4)             # Proscribed tab size for wx
   221         self.SetUseTabs(False)          # Use spaces rather than tabs, or
   210         self.Editor.SetUseTabs(False)          # Use spaces rather than tabs, or
   222                                         # TabTimmy will complain!    
   211                                         # TabTimmy will complain!    
   223         # White space
   212         # White space
   224         self.SetViewWhiteSpace(False)   # Don't view white space
   213         self.Editor.SetViewWhiteSpace(False)   # Don't view white space
   225 
   214 
   226         # EOL: Since we are loading/saving ourselves, and the
   215         # EOL: Since we are loading/saving ourselves, and the
   227         # strings will always have \n's in them, set the STC to
   216         # strings will always have \n's in them, set the STC to
   228         # edit them that way.            
   217         # edit them that way.            
   229         self.SetEOLMode(wx.stc.STC_EOL_LF)
   218         self.Editor.SetEOLMode(wx.stc.STC_EOL_LF)
   230         self.SetViewEOL(False)
   219         self.Editor.SetViewEOL(False)
   231         
   220         
   232         # No right-edge mode indicator
   221         # No right-edge mode indicator
   233         self.SetEdgeMode(stc.STC_EDGE_NONE)
   222         self.Editor.SetEdgeMode(stc.STC_EDGE_NONE)
   234 
   223         
   235         self.Controler = controler
   224         self.Editor.SetModEventMask(wx.stc.STC_MOD_BEFOREINSERT|wx.stc.STC_MOD_BEFOREDELETE)
   236         self.ParentWindow = window
   225 
   237         
   226         self.Editor.Bind(wx.stc.EVT_STC_DO_DROP, self.OnDoDrop, id=ID_PYTHONEDITOR)
   238         self.DisableEvents = True
   227         self.Editor.Bind(wx.EVT_KILL_FOCUS, self.OnKillFocus)
       
   228         self.Editor.Bind(wx.stc.EVT_STC_MODIFIED, self.OnModification, id=ID_PYTHONEDITOR)
       
   229 
       
   230 
       
   231     def __init__(self, parent, controler, window):
       
   232         EditorPanel.__init__(self, parent, "", window, controler)
       
   233         
       
   234         self.DisableEvents = False
   239         self.CurrentAction = None
   235         self.CurrentAction = None
   240         
   236         
   241         self.SetModEventMask(wx.stc.STC_MOD_BEFOREINSERT|wx.stc.STC_MOD_BEFOREDELETE)
   237         img = wx.Bitmap(self.Controler.GetIconPath("Cfile.png"), wx.BITMAP_TYPE_PNG).ConvertToImage()
   242 
   238         self.SetIcon(wx.BitmapFromImage(img.Rescale(16, 16)))
   243         self.Bind(wx.stc.EVT_STC_DO_DROP, self.OnDoDrop, id=ID_PYTHONEDITOR)
   239     
   244         self.Bind(wx.EVT_KILL_FOCUS, self.OnKillFocus)
   240     def __del__(self):
   245         self.Bind(wx.stc.EVT_STC_MODIFIED, self.OnModification, id=ID_PYTHONEDITOR)
   241         self.Controler.OnCloseEditor()
       
   242     
       
   243     def GetTitle(self):
       
   244         fullname = self.Controler.PlugFullName()
       
   245         if not self.Controler.PythonIsSaved():
       
   246             return "~%s~" % fullname
       
   247         return fullname
       
   248     
       
   249     def GetBufferState(self):
       
   250         return self.Controler.GetBufferState()
       
   251         
       
   252     def Undo(self):
       
   253         self.Controler.LoadPrevious()
       
   254         self.RefreshView()
       
   255             
       
   256     def Redo(self):
       
   257         self.Controler.LoadNext()
       
   258         self.RefreshView()
       
   259     
       
   260     def HasNoModel(self):
       
   261         return False
   246     
   262     
   247     def OnModification(self, event):
   263     def OnModification(self, event):
   248         if not self.DisableEvents:
   264         if not self.DisableEvents:
   249             mod_type = event.GetModificationType()
   265             mod_type = event.GetModificationType()
   250             if not (mod_type&wx.stc.STC_PERFORMED_UNDO or mod_type&wx.stc.STC_PERFORMED_REDO):
   266             if not (mod_type&wx.stc.STC_PERFORMED_UNDO or mod_type&wx.stc.STC_PERFORMED_REDO):
   251                 if mod_type&wx.stc.STC_MOD_BEFOREINSERT:
   267                 if mod_type&wx.stc.STC_MOD_BEFOREINSERT:
   252                     if self.CurrentAction == None:
   268                     if self.CurrentAction is None:
   253                         self.StartBuffering()
   269                         self.StartBuffering()
   254                     elif self.CurrentAction[0] != "Add" or self.CurrentAction[1] != event.GetPosition() - 1:
   270                     elif self.CurrentAction[0] != "Add" or self.CurrentAction[1] != event.GetPosition() - 1:
   255                         self.Controler.EndBuffering()
   271                         self.Controler.EndBuffering()
   256                         self.StartBuffering()
   272                         self.StartBuffering()
   257                     self.CurrentAction = ("Add", event.GetPosition())
   273                     self.CurrentAction = ("Add", event.GetPosition())
       
   274                     wx.CallAfter(self.RefreshModel)
   258                 elif mod_type&wx.stc.STC_MOD_BEFOREDELETE:
   275                 elif mod_type&wx.stc.STC_MOD_BEFOREDELETE:
   259                     if self.CurrentAction == None:
   276                     if self.CurrentAction == None:
   260                         self.StartBuffering()
   277                         self.StartBuffering()
   261                     elif self.CurrentAction[0] != "Delete" or self.CurrentAction[1] != event.GetPosition() + 1:
   278                     elif self.CurrentAction[0] != "Delete" or self.CurrentAction[1] != event.GetPosition() + 1:
   262                         self.Controler.EndBuffering()
   279                         self.Controler.EndBuffering()
   263                         self.StartBuffering()
   280                         self.StartBuffering()
   264                     self.CurrentAction = ("Delete", event.GetPosition())
   281                     self.CurrentAction = ("Delete", event.GetPosition())
       
   282                     wx.CallAfter(self.RefreshModel)
   265         event.Skip()
   283         event.Skip()
   266     
   284     
   267     def OnDoDrop(self, event):
   285     def OnDoDrop(self, event):
   268         self.ResetBuffer()
   286         self.ResetBuffer()
   269         wx.CallAfter(self.RefreshModel)
   287         wx.CallAfter(self.RefreshModel)
   270         event.Skip()
   288         event.Skip()
   271 
   289 
   272     def IsViewing(self, name):
       
   273         return self.Name == name
       
   274 
       
   275     # Buffer the last model state
   290     # Buffer the last model state
   276     def RefreshBuffer(self):
   291     def RefreshBuffer(self):
   277         self.Controler.BufferPython()
   292         self.Controler.BufferPython()
   278         if self.ParentWindow:
   293         if self.ParentWindow is not None:
   279             self.ParentWindow.RefreshTitle()
   294             self.ParentWindow.RefreshTitle()
   280             self.ParentWindow.RefreshFileMenu()
   295             self.ParentWindow.RefreshFileMenu()
   281             self.ParentWindow.RefreshEditMenu()
   296             self.ParentWindow.RefreshEditMenu()
       
   297             self.ParentWindow.RefreshPageTitles()
   282     
   298     
   283     def StartBuffering(self):
   299     def StartBuffering(self):
   284         self.Controler.StartBuffering()
   300         self.Controler.StartBuffering()
   285         if self.ParentWindow:
   301         if self.ParentWindow is not None:
   286             self.ParentWindow.RefreshTitle()
   302             self.ParentWindow.RefreshTitle()
   287             self.ParentWindow.RefreshFileMenu()
   303             self.ParentWindow.RefreshFileMenu()
   288             self.ParentWindow.RefreshEditMenu()
   304             self.ParentWindow.RefreshEditMenu()
       
   305             self.ParentWindow.RefreshPageTitles()
   289     
   306     
   290     def ResetBuffer(self):
   307     def ResetBuffer(self):
   291         if self.CurrentAction != None:
   308         if self.CurrentAction != None:
   292             self.Controler.EndBuffering()
   309             self.Controler.EndBuffering()
   293             self.CurrentAction = None
   310             self.CurrentAction = None
   294 
   311 
   295     def RefreshView(self):
   312     def RefreshView(self):
   296         self.ResetBuffer()
   313         self.ResetBuffer()
   297         self.DisableEvents = True
   314         self.DisableEvents = True
   298         old_cursor_pos = self.GetCurrentPos()
   315         old_cursor_pos = self.Editor.GetCurrentPos()
   299         old_text = self.GetText()
   316         old_text = self.Editor.GetText()
   300         new_text = self.Controler.GetPythonCode()
   317         new_text = self.Controler.GetPythonCode()
   301         self.SetText(new_text)
   318         self.Editor.SetText(new_text)
   302         new_cursor_pos = GetCursorPos(old_text, new_text)
   319         new_cursor_pos = GetCursorPos(old_text, new_text)
   303         if new_cursor_pos != None:
   320         if new_cursor_pos != None:
   304             self.GotoPos(new_cursor_pos)
   321             self.Editor.GotoPos(new_cursor_pos)
   305         else:
   322         else:
   306             self.GotoPos(old_cursor_pos)
   323             self.Editor.GotoPos(old_cursor_pos)
   307         self.ScrollToColumn(0)
   324         self.Editor.ScrollToColumn(0)
   308         self.EmptyUndoBuffer()
   325         self.Editor.EmptyUndoBuffer()
   309         self.DisableEvents = False
   326         self.DisableEvents = False
   310         
   327         
   311         self.Colourise(0, -1)
   328         self.Editor.Colourise(0, -1)
   312 
   329 
   313     def RefreshModel(self):
   330     def RefreshModel(self):
   314         self.Controler.SetPythonCode(self.GetText())
   331         self.Controler.SetPythonCode(self.Editor.GetText())
   315 
   332 
   316     def OnKeyPressed(self, event):
   333     def OnKeyPressed(self, event):
   317         if self.CallTipActive():
   334         if self.Editor.CallTipActive():
   318             self.CallTipCancel()
   335             self.Editor.CallTipCancel()
   319         key = event.GetKeyCode()
   336         key = event.GetKeyCode()
   320 
   337 
   321         if key == 32 and event.ControlDown():
   338         if key == 32 and event.ControlDown():
   322             pos = self.GetCurrentPos()
   339             pos = self.Editor.GetCurrentPos()
   323 
   340 
   324             # Tips
   341             # Tips
   325             if event.ShiftDown():
   342             if event.ShiftDown():
   326                 pass
   343                 pass
   327 ##                self.CallTipSetBackground("yellow")
   344 ##                self.CallTipSetBackground("yellow")
   328 ##                self.CallTipShow(pos, 'lots of of text: blah, blah, blah\n\n'
   345 ##                self.CallTipShow(pos, 'lots of of text: blah, blah, blah\n\n'
   329 ##                                 'show some suff, maybe parameters..\n\n'
   346 ##                                 'show some suff, maybe parameters..\n\n'
   330 ##                                 'fubar(param1, param2)')
   347 ##                                 'fubar(param1, param2)')
   331             # Code completion
   348             # Code completion
   332             else:
   349             else:
   333                 self.AutoCompSetIgnoreCase(False)  # so this needs to match
   350                 self.Editor.AutoCompSetIgnoreCase(False)  # so this needs to match
   334 
   351 
   335                 # Images are specified with a appended "?type"
   352                 # Images are specified with a appended "?type"
   336                 self.AutoCompShow(0, " ".join([word + "?1" for word in keyword.kwlist]))
   353                 self.Editor.AutoCompShow(0, " ".join([word + "?1" for word in keyword.kwlist]))
   337         else:
   354         else:
   338             wx.CallAfter(self.RefreshModel)
       
   339             event.Skip()
   355             event.Skip()
   340 
   356 
   341     def OnKillFocus(self, event):
   357     def OnKillFocus(self, event):
   342         self.AutoCompCancel()
   358         self.Editor.AutoCompCancel()
   343         event.Skip()
   359         event.Skip()
   344 
   360 
   345     def OnUpdateUI(self, evt):
   361     def OnUpdateUI(self, evt):
   346         # check for matching braces
   362         # check for matching braces
   347         braceAtCaret = -1
   363         braceAtCaret = -1
   348         braceOpposite = -1
   364         braceOpposite = -1
   349         charBefore = None
   365         charBefore = None
   350         caretPos = self.GetCurrentPos()
   366         caretPos = self.Editor.GetCurrentPos()
   351 
   367 
   352         if caretPos > 0:
   368         if caretPos > 0:
   353             charBefore = self.GetCharAt(caretPos - 1)
   369             charBefore = self.Editor.GetCharAt(caretPos - 1)
   354             styleBefore = self.GetStyleAt(caretPos - 1)
   370             styleBefore = self.Editor.GetStyleAt(caretPos - 1)
   355 
   371 
   356         # check before
   372         # check before
   357         if charBefore and chr(charBefore) in "[]{}()" and styleBefore == stc.STC_P_OPERATOR:
   373         if charBefore and chr(charBefore) in "[]{}()" and styleBefore == stc.STC_P_OPERATOR:
   358             braceAtCaret = caretPos - 1
   374             braceAtCaret = caretPos - 1
   359 
   375 
   360         # check after
   376         # check after
   361         if braceAtCaret < 0:
   377         if braceAtCaret < 0:
   362             charAfter = self.GetCharAt(caretPos)
   378             charAfter = self.Editor.GetCharAt(caretPos)
   363             styleAfter = self.GetStyleAt(caretPos)
   379             styleAfter = self.Editor.GetStyleAt(caretPos)
   364 
   380 
   365             if charAfter and chr(charAfter) in "[]{}()" and styleAfter == stc.STC_P_OPERATOR:
   381             if charAfter and chr(charAfter) in "[]{}()" and styleAfter == stc.STC_P_OPERATOR:
   366                 braceAtCaret = caretPos
   382                 braceAtCaret = caretPos
   367 
   383 
   368         if braceAtCaret >= 0:
   384         if braceAtCaret >= 0:
   369             braceOpposite = self.BraceMatch(braceAtCaret)
   385             braceOpposite = self.Editor.BraceMatch(braceAtCaret)
   370 
   386 
   371         if braceAtCaret != -1  and braceOpposite == -1:
   387         if braceAtCaret != -1  and braceOpposite == -1:
   372             self.BraceBadLight(braceAtCaret)
   388             self.Editor.BraceBadLight(braceAtCaret)
   373         else:
   389         else:
   374             self.BraceHighlight(braceAtCaret, braceOpposite)
   390             self.Editor.BraceHighlight(braceAtCaret, braceOpposite)
   375             #pt = self.PointFromPosition(braceOpposite)
   391             #pt = self.Editor.PointFromPosition(braceOpposite)
   376             #self.Refresh(True, wxRect(pt.x, pt.y, 5,5))
   392             #self.Editor.Refresh(True, wxRect(pt.x, pt.y, 5,5))
   377             #print pt
   393             #print pt
   378             #self.Refresh(False)
   394             #self.Editor.Refresh(False)
   379 
   395 
   380 
   396 
   381     def OnMarginClick(self, evt):
   397     def OnMarginClick(self, evt):
   382         # fold and unfold as needed
   398         # fold and unfold as needed
   383         if evt.GetMargin() == 2:
   399         if evt.GetMargin() == 2:
   384             if evt.GetShift() and evt.GetControl():
   400             if evt.GetShift() and evt.GetControl():
   385                 self.FoldAll()
   401                 self.FoldAll()
   386             else:
   402             else:
   387                 lineClicked = self.LineFromPosition(evt.GetPosition())
   403                 lineClicked = self.Editor.LineFromPosition(evt.GetPosition())
   388 
   404 
   389                 if self.GetFoldLevel(lineClicked) & stc.STC_FOLDLEVELHEADERFLAG:
   405                 if self.Editor.GetFoldLevel(lineClicked) & stc.STC_FOLDLEVELHEADERFLAG:
   390                     if evt.GetShift():
   406                     if evt.GetShift():
   391                         self.SetFoldExpanded(lineClicked, True)
   407                         self.Editor.SetFoldExpanded(lineClicked, True)
   392                         self.Expand(lineClicked, True, True, 1)
   408                         self.Expand(lineClicked, True, True, 1)
   393                     elif evt.GetControl():
   409                     elif evt.GetControl():
   394                         if self.GetFoldExpanded(lineClicked):
   410                         if self.Editor.GetFoldExpanded(lineClicked):
   395                             self.SetFoldExpanded(lineClicked, False)
   411                             self.Editor.SetFoldExpanded(lineClicked, False)
   396                             self.Expand(lineClicked, False, True, 0)
   412                             self.Expand(lineClicked, False, True, 0)
   397                         else:
   413                         else:
   398                             self.SetFoldExpanded(lineClicked, True)
   414                             self.Editor.SetFoldExpanded(lineClicked, True)
   399                             self.Expand(lineClicked, True, True, 100)
   415                             self.Expand(lineClicked, True, True, 100)
   400                     else:
   416                     else:
   401                         self.ToggleFold(lineClicked)
   417                         self.Editor.ToggleFold(lineClicked)
   402 
   418 
   403 
   419 
   404     def FoldAll(self):
   420     def FoldAll(self):
   405         lineCount = self.GetLineCount()
   421         lineCount = self.Editor.GetLineCount()
   406         expanding = True
   422         expanding = True
   407 
   423 
   408         # find out if we are folding or unfolding
   424         # find out if we are folding or unfolding
   409         for lineNum in range(lineCount):
   425         for lineNum in range(lineCount):
   410             if self.GetFoldLevel(lineNum) & stc.STC_FOLDLEVELHEADERFLAG:
   426             if self.Editor.GetFoldLevel(lineNum) & stc.STC_FOLDLEVELHEADERFLAG:
   411                 expanding = not self.GetFoldExpanded(lineNum)
   427                 expanding = not self.Editor.GetFoldExpanded(lineNum)
   412                 break
   428                 break
   413 
   429 
   414         lineNum = 0
   430         lineNum = 0
   415 
   431 
   416         while lineNum < lineCount:
   432         while lineNum < lineCount:
   417             level = self.GetFoldLevel(lineNum)
   433             level = self.Editor.GetFoldLevel(lineNum)
   418             if level & stc.STC_FOLDLEVELHEADERFLAG and \
   434             if level & stc.STC_FOLDLEVELHEADERFLAG and \
   419                (level & stc.STC_FOLDLEVELNUMBERMASK) == stc.STC_FOLDLEVELBASE:
   435                (level & stc.STC_FOLDLEVELNUMBERMASK) == stc.STC_FOLDLEVELBASE:
   420 
   436 
   421                 if expanding:
   437                 if expanding:
   422                     self.SetFoldExpanded(lineNum, True)
   438                     self.Editor.SetFoldExpanded(lineNum, True)
   423                     lineNum = self.Expand(lineNum, True)
   439                     lineNum = self.Expand(lineNum, True)
   424                     lineNum = lineNum - 1
   440                     lineNum = lineNum - 1
   425                 else:
   441                 else:
   426                     lastChild = self.GetLastChild(lineNum, -1)
   442                     lastChild = self.Editor.GetLastChild(lineNum, -1)
   427                     self.SetFoldExpanded(lineNum, False)
   443                     self.Editor.SetFoldExpanded(lineNum, False)
   428 
   444 
   429                     if lastChild > lineNum:
   445                     if lastChild > lineNum:
   430                         self.HideLines(lineNum+1, lastChild)
   446                         self.Editor.HideLines(lineNum+1, lastChild)
   431 
   447 
   432             lineNum = lineNum + 1
   448             lineNum = lineNum + 1
   433 
   449 
   434 
   450 
   435 
   451 
   436     def Expand(self, line, doExpand, force=False, visLevels=0, level=-1):
   452     def Expand(self, line, doExpand, force=False, visLevels=0, level=-1):
   437         lastChild = self.GetLastChild(line, level)
   453         lastChild = self.Editor.GetLastChild(line, level)
   438         line = line + 1
   454         line = line + 1
   439 
   455 
   440         while line <= lastChild:
   456         while line <= lastChild:
   441             if force:
   457             if force:
   442                 if visLevels > 0:
   458                 if visLevels > 0:
   443                     self.ShowLines(line, line)
   459                     self.Editor.ShowLines(line, line)
   444                 else:
   460                 else:
   445                     self.HideLines(line, line)
   461                     self.Editor.HideLines(line, line)
   446             else:
   462             else:
   447                 if doExpand:
   463                 if doExpand:
   448                     self.ShowLines(line, line)
   464                     self.Editor.ShowLines(line, line)
   449 
   465 
   450             if level == -1:
   466             if level == -1:
   451                 level = self.GetFoldLevel(line)
   467                 level = self.Editor.GetFoldLevel(line)
   452 
   468 
   453             if level & stc.STC_FOLDLEVELHEADERFLAG:
   469             if level & stc.STC_FOLDLEVELHEADERFLAG:
   454                 if force:
   470                 if force:
   455                     if visLevels > 1:
   471                     if visLevels > 1:
   456                         self.SetFoldExpanded(line, True)
   472                         self.Editor.SetFoldExpanded(line, True)
   457                     else:
   473                     else:
   458                         self.SetFoldExpanded(line, False)
   474                         self.Editor.SetFoldExpanded(line, False)
   459 
   475 
   460                     line = self.Expand(line, doExpand, force, visLevels-1)
   476                     line = self.Expand(line, doExpand, force, visLevels-1)
   461 
   477 
   462                 else:
   478                 else:
   463                     if doExpand and self.GetFoldExpanded(line):
   479                     if doExpand and self.Editor.GetFoldExpanded(line):
   464                         line = self.Expand(line, True, force, visLevels-1)
   480                         line = self.Expand(line, True, force, visLevels-1)
   465                     else:
   481                     else:
   466                         line = self.Expand(line, False, force, visLevels-1)
   482                         line = self.Expand(line, False, force, visLevels-1)
   467             else:
   483             else:
   468                 line = line + 1
   484                 line = line + 1
   469 
   485 
   470         return line
   486         return line
   471    
   487 
   472 
   488     def Cut(self):
   473 #-------------------------------------------------------------------------------
   489         self.ResetBuffer()
   474 #                          PythonEditor Main Frame Class
   490         self.DisableEvents = True
   475 #-------------------------------------------------------------------------------
   491         self.Editor.CmdKeyExecute(wx.stc.STC_CMD_CUT)
   476 
   492         self.DisableEvents = False
   477 
   493         self.RefreshModel()
   478 [ID_PYTHONEDITORFRAME, 
   494         self.RefreshBuffer()
   479 ] = [wx.NewId() for _init_ctrls in range(1)]
   495     
   480 
   496     def Copy(self):
   481 class PythonEditorFrame(wx.Frame):
   497         self.Editor.CmdKeyExecute(wx.stc.STC_CMD_COPY)
   482     
   498     
   483     if wx.VERSION < (2, 6, 0):
   499     def Paste(self):
   484         def Bind(self, event, function, id = None):
   500         self.ResetBuffer()
   485             if id is not None:
   501         self.DisableEvents = True
   486                 event(self, id, function)
   502         self.Editor.CmdKeyExecute(wx.stc.STC_CMD_PASTE)
   487             else:
   503         self.DisableEvents = False
   488                 event(self, function)
   504         self.RefreshModel()
   489     
   505         self.RefreshBuffer()
   490     def _init_coll_EditMenu_Items(self, parent):
       
   491         AppendMenu(parent, help='', id=wx.ID_REFRESH,
       
   492               kind=wx.ITEM_NORMAL, text=_(u'Refresh\tCTRL+R'))
       
   493         AppendMenu(parent, help='', id=wx.ID_UNDO,
       
   494               kind=wx.ITEM_NORMAL, text=_(u'Undo\tCTRL+Z'))
       
   495         AppendMenu(parent, help='', id=wx.ID_REDO,
       
   496               kind=wx.ITEM_NORMAL, text=_(u'Redo\tCTRL+Y'))
       
   497         self.Bind(wx.EVT_MENU, self.OnRefreshMenu, id=wx.ID_REFRESH)
       
   498         self.Bind(wx.EVT_MENU, self.OnUndoMenu, id=wx.ID_UNDO)
       
   499         self.Bind(wx.EVT_MENU, self.OnRedoMenu, id=wx.ID_REDO)
       
   500     
       
   501     def _init_coll_MenuBar_Menus(self, parent):
       
   502         parent.Append(menu=self.EditMenu, title=_(u'&Edit'))
       
   503     
       
   504     def _init_utils(self):
       
   505         self.MenuBar = wx.MenuBar()
       
   506 
       
   507         self.EditMenu = wx.Menu(title='')
       
   508         
       
   509         self._init_coll_MenuBar_Menus(self.MenuBar)
       
   510         self._init_coll_EditMenu_Items(self.EditMenu)
       
   511         
       
   512     def _init_ctrls(self, prnt):
       
   513         wx.Frame.__init__(self, id=ID_PYTHONEDITORFRAME, name=u'PythonEditor',
       
   514               parent=prnt, pos=wx.DefaultPosition, size=wx.Size(800, 650),
       
   515               style=wx.DEFAULT_FRAME_STYLE, title=_(u'PythonEditor'))
       
   516         self._init_utils()
       
   517         self.SetClientSize(wx.Size(1000, 600))
       
   518         self.SetMenuBar(self.MenuBar)
       
   519         self.Bind(wx.EVT_CLOSE, self.OnCloseFrame)
       
   520         
       
   521         self.Bind(wx.EVT_MENU, self.OnSaveMenu, id=wx.ID_SAVE)
       
   522         accel = wx.AcceleratorTable([wx.AcceleratorEntry(wx.ACCEL_CTRL, 83, wx.ID_SAVE)])
       
   523         self.SetAcceleratorTable(accel)
       
   524         
       
   525         if wx.VERSION >= (2, 8, 0):
       
   526             self.AUIManager = wx.aui.AuiManager(self)
       
   527             self.AUIManager.SetDockSizeConstraint(0.5, 0.5)
       
   528         
       
   529         self.PythonEdited = PythonEditor(self, self, self.Controler)
       
   530         if wx.VERSION < (2, 8, 0):
       
   531             self.MainSizer = wx.BoxSizer(wx.VERTICAL)
       
   532             self.MainSizer.AddWindow(self.PythonEdited, 0, border=0, flag=wx.GROW)
       
   533             self.SetSizer(self.MainSizer)
       
   534         else:
       
   535             self.AUIManager.AddPane(self.PythonEdited, wx.aui.AuiPaneInfo().CentrePane())
       
   536             
       
   537         self.StatusBar = wx.StatusBar( name='HelpBar',
       
   538               parent=self, style=wx.ST_SIZEGRIP)
       
   539         self.SetStatusBar(self.StatusBar)
       
   540         
       
   541         if wx.VERSION >= (2, 8, 0):
       
   542             self.AUIManager.Update()
       
   543     
       
   544     def __init__(self, parent, controler):
       
   545         self.Controler = controler
       
   546         
       
   547         self._init_ctrls(parent)
       
   548         
       
   549         self.PythonEdited.RefreshView()
       
   550         self.RefreshTitle()
       
   551         self.RefreshEditMenu()
       
   552 
       
   553     def OnCloseFrame(self, event):
       
   554         if wx.VERSION >= (2, 8, 0):
       
   555             self.AUIManager.UnInit()
       
   556         if getattr(self, "_onclose", None) is not None:
       
   557             self._onclose()
       
   558         event.Skip()
       
   559 
       
   560     def OnSaveMenu(self, event):
       
   561         if getattr(self, "_onsave", None) != None:
       
   562             self._onsave()
       
   563         self.RefreshTitle()
       
   564         self.RefreshEditMenu()
       
   565 
       
   566     def RefreshTitle(self):
       
   567         title = _("PythonEditor")
       
   568         self.SetTitle("%s - %s"%(title, self.Controler.GetFilename()))
       
   569         
       
   570 #-------------------------------------------------------------------------------
       
   571 #                          Edit Project Menu Functions
       
   572 #-------------------------------------------------------------------------------
       
   573 
       
   574     def RefreshFileMenu(self):
       
   575         pass
       
   576 
       
   577     def RefreshEditMenu(self):
       
   578         undo, redo = self.Controler.GetBufferState()
       
   579         self.EditMenu.Enable(wx.ID_UNDO, undo)
       
   580         self.EditMenu.Enable(wx.ID_REDO, redo)
       
   581 
       
   582     def OnRefreshMenu(self, event):
       
   583         self.PythonEdited.RefreshView()
       
   584 
       
   585     def OnUndoMenu(self, event):
       
   586         self.Controler.LoadPrevious()
       
   587         self.PythonEdited.RefreshView()
       
   588         self.RefreshTitle()
       
   589         self.RefreshEditMenu()
       
   590     
       
   591     def OnRedoMenu(self, event):
       
   592         self.Controler.LoadNext()
       
   593         self.PythonEdited.RefreshView()
       
   594         self.RefreshTitle()
       
   595         self.RefreshEditMenu()
       
   596         
       
   597