py_ext/PythonEditor.py
changeset 920 1499a4d225db
parent 814 5743cbdff669
child 1057 3837e165b3f9
equal deleted inserted replaced
919:4a36e38e51d3 920:1499a4d225db
    55         return None
    55         return None
    56 
    56 
    57 class PythonEditor(ConfTreeNodeEditor):
    57 class PythonEditor(ConfTreeNodeEditor):
    58 
    58 
    59     fold_symbols = 3
    59     fold_symbols = 3
    60     
    60     CONFNODEEDITOR_TABS = [
    61     def _init_ConfNodeEditor(self, prnt):
    61         (_("Python code"), "_create_PythonCodeEditor")]
    62         self.ConfNodeEditor = stc.StyledTextCtrl(id=ID_PYTHONEDITOR, parent=prnt,
    62     
       
    63     def _create_PythonCodeEditor(self, prnt):
       
    64         self.PythonCodeEditor = stc.StyledTextCtrl(id=ID_PYTHONEDITOR, parent=prnt,
    63                  name="TextViewer", pos=wx.DefaultPosition, 
    65                  name="TextViewer", pos=wx.DefaultPosition, 
    64                  size=wx.DefaultSize, style=0)
    66                  size=wx.DefaultSize, style=0)
    65         self.ConfNodeEditor.ParentWindow = self
    67         self.PythonCodeEditor.ParentWindow = self
    66         
    68         
    67         self.ConfNodeEditor.CmdKeyAssign(ord('B'), stc.STC_SCMOD_CTRL, stc.STC_CMD_ZOOMIN)
    69         self.PythonCodeEditor.CmdKeyAssign(ord('B'), stc.STC_SCMOD_CTRL, stc.STC_CMD_ZOOMIN)
    68         self.ConfNodeEditor.CmdKeyAssign(ord('N'), stc.STC_SCMOD_CTRL, stc.STC_CMD_ZOOMOUT)
    70         self.PythonCodeEditor.CmdKeyAssign(ord('N'), stc.STC_SCMOD_CTRL, stc.STC_CMD_ZOOMOUT)
    69 
    71 
    70         self.ConfNodeEditor.SetLexer(stc.STC_LEX_PYTHON)
    72         self.PythonCodeEditor.SetLexer(stc.STC_LEX_PYTHON)
    71         self.ConfNodeEditor.SetKeyWords(0, " ".join(keyword.kwlist))
    73         self.PythonCodeEditor.SetKeyWords(0, " ".join(keyword.kwlist))
    72 
    74 
    73         self.ConfNodeEditor.SetProperty("fold", "1")
    75         self.PythonCodeEditor.SetProperty("fold", "1")
    74         self.ConfNodeEditor.SetProperty("tab.timmy.whinge.level", "1")
    76         self.PythonCodeEditor.SetProperty("tab.timmy.whinge.level", "1")
    75         self.ConfNodeEditor.SetMargins(0,0)
    77         self.PythonCodeEditor.SetMargins(0,0)
    76 
    78 
    77         self.ConfNodeEditor.SetViewWhiteSpace(False)
    79         self.PythonCodeEditor.SetViewWhiteSpace(False)
    78         
    80         
    79         self.ConfNodeEditor.SetEdgeMode(stc.STC_EDGE_BACKGROUND)
    81         self.PythonCodeEditor.SetEdgeMode(stc.STC_EDGE_BACKGROUND)
    80         self.ConfNodeEditor.SetEdgeColumn(78)
    82         self.PythonCodeEditor.SetEdgeColumn(78)
    81 
    83 
    82         # Set up the numbers in the margin for margin #1
    84         # Set up the numbers in the margin for margin #1
    83         self.ConfNodeEditor.SetMarginType(1, wx.stc.STC_MARGIN_NUMBER)
    85         self.PythonCodeEditor.SetMarginType(1, wx.stc.STC_MARGIN_NUMBER)
    84         # Reasonable value for, say, 4-5 digits using a mono font (40 pix)
    86         # Reasonable value for, say, 4-5 digits using a mono font (40 pix)
    85         self.ConfNodeEditor.SetMarginWidth(1, 40)
    87         self.PythonCodeEditor.SetMarginWidth(1, 40)
    86 
    88 
    87         # Setup a margin to hold fold markers
    89         # Setup a margin to hold fold markers
    88         self.ConfNodeEditor.SetMarginType(2, stc.STC_MARGIN_SYMBOL)
    90         self.PythonCodeEditor.SetMarginType(2, stc.STC_MARGIN_SYMBOL)
    89         self.ConfNodeEditor.SetMarginMask(2, stc.STC_MASK_FOLDERS)
    91         self.PythonCodeEditor.SetMarginMask(2, stc.STC_MASK_FOLDERS)
    90         self.ConfNodeEditor.SetMarginSensitive(2, True)
    92         self.PythonCodeEditor.SetMarginSensitive(2, True)
    91         self.ConfNodeEditor.SetMarginWidth(2, 12)
    93         self.PythonCodeEditor.SetMarginWidth(2, 12)
    92 
    94 
    93         if self.fold_symbols == 0:
    95         if self.fold_symbols == 0:
    94             # Arrow pointing right for contracted folders, arrow pointing down for expanded
    96             # Arrow pointing right for contracted folders, arrow pointing down for expanded
    95             self.ConfNodeEditor.MarkerDefine(stc.STC_MARKNUM_FOLDEROPEN,    stc.STC_MARK_ARROWDOWN, "black", "black")
    97             self.PythonCodeEditor.MarkerDefine(stc.STC_MARKNUM_FOLDEROPEN,    stc.STC_MARK_ARROWDOWN, "black", "black")
    96             self.ConfNodeEditor.MarkerDefine(stc.STC_MARKNUM_FOLDER,        stc.STC_MARK_ARROW, "black", "black")
    98             self.PythonCodeEditor.MarkerDefine(stc.STC_MARKNUM_FOLDER,        stc.STC_MARK_ARROW, "black", "black")
    97             self.ConfNodeEditor.MarkerDefine(stc.STC_MARKNUM_FOLDERSUB,     stc.STC_MARK_EMPTY, "black", "black")
    99             self.PythonCodeEditor.MarkerDefine(stc.STC_MARKNUM_FOLDERSUB,     stc.STC_MARK_EMPTY, "black", "black")
    98             self.ConfNodeEditor.MarkerDefine(stc.STC_MARKNUM_FOLDERTAIL,    stc.STC_MARK_EMPTY, "black", "black")
   100             self.PythonCodeEditor.MarkerDefine(stc.STC_MARKNUM_FOLDERTAIL,    stc.STC_MARK_EMPTY, "black", "black")
    99             self.ConfNodeEditor.MarkerDefine(stc.STC_MARKNUM_FOLDEREND,     stc.STC_MARK_EMPTY,     "white", "black")
   101             self.PythonCodeEditor.MarkerDefine(stc.STC_MARKNUM_FOLDEREND,     stc.STC_MARK_EMPTY,     "white", "black")
   100             self.ConfNodeEditor.MarkerDefine(stc.STC_MARKNUM_FOLDEROPENMID, stc.STC_MARK_EMPTY,     "white", "black")
   102             self.PythonCodeEditor.MarkerDefine(stc.STC_MARKNUM_FOLDEROPENMID, stc.STC_MARK_EMPTY,     "white", "black")
   101             self.ConfNodeEditor.MarkerDefine(stc.STC_MARKNUM_FOLDERMIDTAIL, stc.STC_MARK_EMPTY,     "white", "black")
   103             self.PythonCodeEditor.MarkerDefine(stc.STC_MARKNUM_FOLDERMIDTAIL, stc.STC_MARK_EMPTY,     "white", "black")
   102             
   104             
   103         elif self.fold_symbols == 1:
   105         elif self.fold_symbols == 1:
   104             # Plus for contracted folders, minus for expanded
   106             # Plus for contracted folders, minus for expanded
   105             self.ConfNodeEditor.MarkerDefine(stc.STC_MARKNUM_FOLDEROPEN,    stc.STC_MARK_MINUS, "white", "black")
   107             self.PythonCodeEditor.MarkerDefine(stc.STC_MARKNUM_FOLDEROPEN,    stc.STC_MARK_MINUS, "white", "black")
   106             self.ConfNodeEditor.MarkerDefine(stc.STC_MARKNUM_FOLDER,        stc.STC_MARK_PLUS,  "white", "black")
   108             self.PythonCodeEditor.MarkerDefine(stc.STC_MARKNUM_FOLDER,        stc.STC_MARK_PLUS,  "white", "black")
   107             self.ConfNodeEditor.MarkerDefine(stc.STC_MARKNUM_FOLDERSUB,     stc.STC_MARK_EMPTY, "white", "black")
   109             self.PythonCodeEditor.MarkerDefine(stc.STC_MARKNUM_FOLDERSUB,     stc.STC_MARK_EMPTY, "white", "black")
   108             self.ConfNodeEditor.MarkerDefine(stc.STC_MARKNUM_FOLDERTAIL,    stc.STC_MARK_EMPTY, "white", "black")
   110             self.PythonCodeEditor.MarkerDefine(stc.STC_MARKNUM_FOLDERTAIL,    stc.STC_MARK_EMPTY, "white", "black")
   109             self.ConfNodeEditor.MarkerDefine(stc.STC_MARKNUM_FOLDEREND,     stc.STC_MARK_EMPTY, "white", "black")
   111             self.PythonCodeEditor.MarkerDefine(stc.STC_MARKNUM_FOLDEREND,     stc.STC_MARK_EMPTY, "white", "black")
   110             self.ConfNodeEditor.MarkerDefine(stc.STC_MARKNUM_FOLDEROPENMID, stc.STC_MARK_EMPTY, "white", "black")
   112             self.PythonCodeEditor.MarkerDefine(stc.STC_MARKNUM_FOLDEROPENMID, stc.STC_MARK_EMPTY, "white", "black")
   111             self.ConfNodeEditor.MarkerDefine(stc.STC_MARKNUM_FOLDERMIDTAIL, stc.STC_MARK_EMPTY, "white", "black")
   113             self.PythonCodeEditor.MarkerDefine(stc.STC_MARKNUM_FOLDERMIDTAIL, stc.STC_MARK_EMPTY, "white", "black")
   112 
   114 
   113         elif self.fold_symbols == 2:
   115         elif self.fold_symbols == 2:
   114             # Like a flattened tree control using circular headers and curved joins
   116             # Like a flattened tree control using circular headers and curved joins
   115             self.ConfNodeEditor.MarkerDefine(stc.STC_MARKNUM_FOLDEROPEN,    stc.STC_MARK_CIRCLEMINUS,          "white", "#404040")
   117             self.PythonCodeEditor.MarkerDefine(stc.STC_MARKNUM_FOLDEROPEN,    stc.STC_MARK_CIRCLEMINUS,          "white", "#404040")
   116             self.ConfNodeEditor.MarkerDefine(stc.STC_MARKNUM_FOLDER,        stc.STC_MARK_CIRCLEPLUS,           "white", "#404040")
   118             self.PythonCodeEditor.MarkerDefine(stc.STC_MARKNUM_FOLDER,        stc.STC_MARK_CIRCLEPLUS,           "white", "#404040")
   117             self.ConfNodeEditor.MarkerDefine(stc.STC_MARKNUM_FOLDERSUB,     stc.STC_MARK_VLINE,                "white", "#404040")
   119             self.PythonCodeEditor.MarkerDefine(stc.STC_MARKNUM_FOLDERSUB,     stc.STC_MARK_VLINE,                "white", "#404040")
   118             self.ConfNodeEditor.MarkerDefine(stc.STC_MARKNUM_FOLDERTAIL,    stc.STC_MARK_LCORNERCURVE,         "white", "#404040")
   120             self.PythonCodeEditor.MarkerDefine(stc.STC_MARKNUM_FOLDERTAIL,    stc.STC_MARK_LCORNERCURVE,         "white", "#404040")
   119             self.ConfNodeEditor.MarkerDefine(stc.STC_MARKNUM_FOLDEREND,     stc.STC_MARK_CIRCLEPLUSCONNECTED,  "white", "#404040")
   121             self.PythonCodeEditor.MarkerDefine(stc.STC_MARKNUM_FOLDEREND,     stc.STC_MARK_CIRCLEPLUSCONNECTED,  "white", "#404040")
   120             self.ConfNodeEditor.MarkerDefine(stc.STC_MARKNUM_FOLDEROPENMID, stc.STC_MARK_CIRCLEMINUSCONNECTED, "white", "#404040")
   122             self.PythonCodeEditor.MarkerDefine(stc.STC_MARKNUM_FOLDEROPENMID, stc.STC_MARK_CIRCLEMINUSCONNECTED, "white", "#404040")
   121             self.ConfNodeEditor.MarkerDefine(stc.STC_MARKNUM_FOLDERMIDTAIL, stc.STC_MARK_TCORNERCURVE,         "white", "#404040")
   123             self.PythonCodeEditor.MarkerDefine(stc.STC_MARKNUM_FOLDERMIDTAIL, stc.STC_MARK_TCORNERCURVE,         "white", "#404040")
   122 
   124 
   123         elif self.fold_symbols == 3:
   125         elif self.fold_symbols == 3:
   124             # Like a flattened tree control using square headers
   126             # Like a flattened tree control using square headers
   125             self.ConfNodeEditor.MarkerDefine(stc.STC_MARKNUM_FOLDEROPEN,    stc.STC_MARK_BOXMINUS,          "white", "#808080")
   127             self.PythonCodeEditor.MarkerDefine(stc.STC_MARKNUM_FOLDEROPEN,    stc.STC_MARK_BOXMINUS,          "white", "#808080")
   126             self.ConfNodeEditor.MarkerDefine(stc.STC_MARKNUM_FOLDER,        stc.STC_MARK_BOXPLUS,           "white", "#808080")
   128             self.PythonCodeEditor.MarkerDefine(stc.STC_MARKNUM_FOLDER,        stc.STC_MARK_BOXPLUS,           "white", "#808080")
   127             self.ConfNodeEditor.MarkerDefine(stc.STC_MARKNUM_FOLDERSUB,     stc.STC_MARK_VLINE,             "white", "#808080")
   129             self.PythonCodeEditor.MarkerDefine(stc.STC_MARKNUM_FOLDERSUB,     stc.STC_MARK_VLINE,             "white", "#808080")
   128             self.ConfNodeEditor.MarkerDefine(stc.STC_MARKNUM_FOLDERTAIL,    stc.STC_MARK_LCORNER,           "white", "#808080")
   130             self.PythonCodeEditor.MarkerDefine(stc.STC_MARKNUM_FOLDERTAIL,    stc.STC_MARK_LCORNER,           "white", "#808080")
   129             self.ConfNodeEditor.MarkerDefine(stc.STC_MARKNUM_FOLDEREND,     stc.STC_MARK_BOXPLUSCONNECTED,  "white", "#808080")
   131             self.PythonCodeEditor.MarkerDefine(stc.STC_MARKNUM_FOLDEREND,     stc.STC_MARK_BOXPLUSCONNECTED,  "white", "#808080")
   130             self.ConfNodeEditor.MarkerDefine(stc.STC_MARKNUM_FOLDEROPENMID, stc.STC_MARK_BOXMINUSCONNECTED, "white", "#808080")
   132             self.PythonCodeEditor.MarkerDefine(stc.STC_MARKNUM_FOLDEROPENMID, stc.STC_MARK_BOXMINUSCONNECTED, "white", "#808080")
   131             self.ConfNodeEditor.MarkerDefine(stc.STC_MARKNUM_FOLDERMIDTAIL, stc.STC_MARK_TCORNER,           "white", "#808080")
   133             self.PythonCodeEditor.MarkerDefine(stc.STC_MARKNUM_FOLDERMIDTAIL, stc.STC_MARK_TCORNER,           "white", "#808080")
   132 
   134 
   133 
   135 
   134         self.ConfNodeEditor.Bind(stc.EVT_STC_UPDATEUI, self.OnUpdateUI)
   136         self.PythonCodeEditor.Bind(stc.EVT_STC_UPDATEUI, self.OnUpdateUI)
   135         self.ConfNodeEditor.Bind(stc.EVT_STC_MARGINCLICK, self.OnMarginClick)
   137         self.PythonCodeEditor.Bind(stc.EVT_STC_MARGINCLICK, self.OnMarginClick)
   136         self.ConfNodeEditor.Bind(wx.EVT_KEY_DOWN, self.OnKeyPressed)
   138         self.PythonCodeEditor.Bind(wx.EVT_KEY_DOWN, self.OnKeyPressed)
   137 
   139 
   138         # Global default style
   140         # Global default style
   139         if wx.Platform == '__WXMSW__':
   141         if wx.Platform == '__WXMSW__':
   140             self.ConfNodeEditor.StyleSetSpec(stc.STC_STYLE_DEFAULT, 'fore:#000000,back:#FFFFFF,face:Courier New')
   142             self.PythonCodeEditor.StyleSetSpec(stc.STC_STYLE_DEFAULT, 'fore:#000000,back:#FFFFFF,face:Courier New')
   141         elif wx.Platform == '__WXMAC__':
   143         elif wx.Platform == '__WXMAC__':
   142             # TODO: if this looks fine on Linux too, remove the Mac-specific case 
   144             # TODO: if this looks fine on Linux too, remove the Mac-specific case 
   143             # and use this whenever OS != MSW.
   145             # and use this whenever OS != MSW.
   144             self.ConfNodeEditor.StyleSetSpec(stc.STC_STYLE_DEFAULT, 'fore:#000000,back:#FFFFFF,face:Monaco')
   146             self.PythonCodeEditor.StyleSetSpec(stc.STC_STYLE_DEFAULT, 'fore:#000000,back:#FFFFFF,face:Monaco')
   145         else:
   147         else:
   146             defsize = wx.SystemSettings.GetFont(wx.SYS_ANSI_FIXED_FONT).GetPointSize()
   148             defsize = wx.SystemSettings.GetFont(wx.SYS_ANSI_FIXED_FONT).GetPointSize()
   147             self.ConfNodeEditor.StyleSetSpec(stc.STC_STYLE_DEFAULT, 'fore:#000000,back:#FFFFFF,face:Courier,size:%d'%defsize)
   149             self.PythonCodeEditor.StyleSetSpec(stc.STC_STYLE_DEFAULT, 'fore:#000000,back:#FFFFFF,face:Courier,size:%d'%defsize)
   148 
   150 
   149         # Clear styles and revert to default.
   151         # Clear styles and revert to default.
   150         self.ConfNodeEditor.StyleClearAll()
   152         self.PythonCodeEditor.StyleClearAll()
   151 
   153 
   152         # Following style specs only indicate differences from default.
   154         # Following style specs only indicate differences from default.
   153         # The rest remains unchanged.
   155         # The rest remains unchanged.
   154 
   156 
   155         # Line numbers in margin
   157         # Line numbers in margin
   156         self.ConfNodeEditor.StyleSetSpec(wx.stc.STC_STYLE_LINENUMBER,'fore:#000000,back:#99A9C2')    
   158         self.PythonCodeEditor.StyleSetSpec(wx.stc.STC_STYLE_LINENUMBER,'fore:#000000,back:#99A9C2')    
   157         # Highlighted brace
   159         # Highlighted brace
   158         self.ConfNodeEditor.StyleSetSpec(wx.stc.STC_STYLE_BRACELIGHT,'fore:#00009D,back:#FFFF00')
   160         self.PythonCodeEditor.StyleSetSpec(wx.stc.STC_STYLE_BRACELIGHT,'fore:#00009D,back:#FFFF00')
   159         # Unmatched brace
   161         # Unmatched brace
   160         self.ConfNodeEditor.StyleSetSpec(wx.stc.STC_STYLE_BRACEBAD,'fore:#00009D,back:#FF0000')
   162         self.PythonCodeEditor.StyleSetSpec(wx.stc.STC_STYLE_BRACEBAD,'fore:#00009D,back:#FF0000')
   161         # Indentation guide
   163         # Indentation guide
   162         self.ConfNodeEditor.StyleSetSpec(wx.stc.STC_STYLE_INDENTGUIDE, "fore:#CDCDCD")
   164         self.PythonCodeEditor.StyleSetSpec(wx.stc.STC_STYLE_INDENTGUIDE, "fore:#CDCDCD")
   163 
   165 
   164         # Python styles
   166         # Python styles
   165         self.ConfNodeEditor.StyleSetSpec(wx.stc.STC_P_DEFAULT, 'fore:#000000')
   167         self.PythonCodeEditor.StyleSetSpec(wx.stc.STC_P_DEFAULT, 'fore:#000000')
   166         # Comments
   168         # Comments
   167         self.ConfNodeEditor.StyleSetSpec(wx.stc.STC_P_COMMENTLINE,  'fore:#008000,back:#F0FFF0')
   169         self.PythonCodeEditor.StyleSetSpec(wx.stc.STC_P_COMMENTLINE,  'fore:#008000,back:#F0FFF0')
   168         self.ConfNodeEditor.StyleSetSpec(wx.stc.STC_P_COMMENTBLOCK, 'fore:#008000,back:#F0FFF0')
   170         self.PythonCodeEditor.StyleSetSpec(wx.stc.STC_P_COMMENTBLOCK, 'fore:#008000,back:#F0FFF0')
   169         # Numbers
   171         # Numbers
   170         self.ConfNodeEditor.StyleSetSpec(wx.stc.STC_P_NUMBER, 'fore:#008080')
   172         self.PythonCodeEditor.StyleSetSpec(wx.stc.STC_P_NUMBER, 'fore:#008080')
   171         # Strings and characters
   173         # Strings and characters
   172         self.ConfNodeEditor.StyleSetSpec(wx.stc.STC_P_STRING, 'fore:#800080')
   174         self.PythonCodeEditor.StyleSetSpec(wx.stc.STC_P_STRING, 'fore:#800080')
   173         self.ConfNodeEditor.StyleSetSpec(wx.stc.STC_P_CHARACTER, 'fore:#800080')
   175         self.PythonCodeEditor.StyleSetSpec(wx.stc.STC_P_CHARACTER, 'fore:#800080')
   174         # Keywords
   176         # Keywords
   175         self.ConfNodeEditor.StyleSetSpec(wx.stc.STC_P_WORD, 'fore:#000080,bold')
   177         self.PythonCodeEditor.StyleSetSpec(wx.stc.STC_P_WORD, 'fore:#000080,bold')
   176         # Triple quotes
   178         # Triple quotes
   177         self.ConfNodeEditor.StyleSetSpec(wx.stc.STC_P_TRIPLE, 'fore:#800080,back:#FFFFEA')
   179         self.PythonCodeEditor.StyleSetSpec(wx.stc.STC_P_TRIPLE, 'fore:#800080,back:#FFFFEA')
   178         self.ConfNodeEditor.StyleSetSpec(wx.stc.STC_P_TRIPLEDOUBLE, 'fore:#800080,back:#FFFFEA')
   180         self.PythonCodeEditor.StyleSetSpec(wx.stc.STC_P_TRIPLEDOUBLE, 'fore:#800080,back:#FFFFEA')
   179         # Class names
   181         # Class names
   180         self.ConfNodeEditor.StyleSetSpec(wx.stc.STC_P_CLASSNAME, 'fore:#0000FF,bold')
   182         self.PythonCodeEditor.StyleSetSpec(wx.stc.STC_P_CLASSNAME, 'fore:#0000FF,bold')
   181         # Function names
   183         # Function names
   182         self.ConfNodeEditor.StyleSetSpec(wx.stc.STC_P_DEFNAME, 'fore:#008080,bold')
   184         self.PythonCodeEditor.StyleSetSpec(wx.stc.STC_P_DEFNAME, 'fore:#008080,bold')
   183         # Operators
   185         # Operators
   184         self.ConfNodeEditor.StyleSetSpec(wx.stc.STC_P_OPERATOR, 'fore:#800000,bold')
   186         self.PythonCodeEditor.StyleSetSpec(wx.stc.STC_P_OPERATOR, 'fore:#800000,bold')
   185         # Identifiers. I leave this as not bold because everything seems
   187         # Identifiers. I leave this as not bold because everything seems
   186         # to be an identifier if it doesn't match the above criterae
   188         # to be an identifier if it doesn't match the above criterae
   187         self.ConfNodeEditor.StyleSetSpec(wx.stc.STC_P_IDENTIFIER, 'fore:#000000')
   189         self.PythonCodeEditor.StyleSetSpec(wx.stc.STC_P_IDENTIFIER, 'fore:#000000')
   188 
   190 
   189         # Caret color
   191         # Caret color
   190         self.ConfNodeEditor.SetCaretForeground("BLUE")
   192         self.PythonCodeEditor.SetCaretForeground("BLUE")
   191         # Selection background
   193         # Selection background
   192         self.ConfNodeEditor.SetSelBackground(1, '#66CCFF')
   194         self.PythonCodeEditor.SetSelBackground(1, '#66CCFF')
   193 
   195 
   194         self.ConfNodeEditor.SetSelBackground(True, wx.SystemSettings_GetColour(wx.SYS_COLOUR_HIGHLIGHT))
   196         self.PythonCodeEditor.SetSelBackground(True, wx.SystemSettings_GetColour(wx.SYS_COLOUR_HIGHLIGHT))
   195         self.ConfNodeEditor.SetSelForeground(True, wx.SystemSettings_GetColour(wx.SYS_COLOUR_HIGHLIGHTTEXT))
   197         self.PythonCodeEditor.SetSelForeground(True, wx.SystemSettings_GetColour(wx.SYS_COLOUR_HIGHLIGHTTEXT))
   196         
   198         
   197         # register some images for use in the AutoComplete box.
   199         # register some images for use in the AutoComplete box.
   198         #self.RegisterImage(1, images.getSmilesBitmap())
   200         #self.RegisterImage(1, images.getSmilesBitmap())
   199         self.ConfNodeEditor.RegisterImage(1, 
   201         self.PythonCodeEditor.RegisterImage(1, 
   200             wx.ArtProvider.GetBitmap(wx.ART_DELETE, size=(16,16)))
   202             wx.ArtProvider.GetBitmap(wx.ART_DELETE, size=(16,16)))
   201         self.ConfNodeEditor.RegisterImage(2, 
   203         self.PythonCodeEditor.RegisterImage(2, 
   202             wx.ArtProvider.GetBitmap(wx.ART_NEW, size=(16,16)))
   204             wx.ArtProvider.GetBitmap(wx.ART_NEW, size=(16,16)))
   203         self.ConfNodeEditor.RegisterImage(3, 
   205         self.PythonCodeEditor.RegisterImage(3, 
   204             wx.ArtProvider.GetBitmap(wx.ART_COPY, size=(16,16)))
   206             wx.ArtProvider.GetBitmap(wx.ART_COPY, size=(16,16)))
   205 
   207 
   206         # Indentation and tab stuff
   208         # Indentation and tab stuff
   207         self.ConfNodeEditor.SetIndent(4)               # Proscribed indent size for wx
   209         self.PythonCodeEditor.SetIndent(4)               # Proscribed indent size for wx
   208         self.ConfNodeEditor.SetIndentationGuides(True) # Show indent guides
   210         self.PythonCodeEditor.SetIndentationGuides(True) # Show indent guides
   209         self.ConfNodeEditor.SetBackSpaceUnIndents(True)# Backspace unindents rather than delete 1 space
   211         self.PythonCodeEditor.SetBackSpaceUnIndents(True)# Backspace unindents rather than delete 1 space
   210         self.ConfNodeEditor.SetTabIndents(True)        # Tab key indents
   212         self.PythonCodeEditor.SetTabIndents(True)        # Tab key indents
   211         self.ConfNodeEditor.SetTabWidth(4)             # Proscribed tab size for wx
   213         self.PythonCodeEditor.SetTabWidth(4)             # Proscribed tab size for wx
   212         self.ConfNodeEditor.SetUseTabs(False)          # Use spaces rather than tabs, or
   214         self.PythonCodeEditor.SetUseTabs(False)          # Use spaces rather than tabs, or
   213                                         # TabTimmy will complain!    
   215                                         # TabTimmy will complain!    
   214         # White space
   216         # White space
   215         self.ConfNodeEditor.SetViewWhiteSpace(False)   # Don't view white space
   217         self.PythonCodeEditor.SetViewWhiteSpace(False)   # Don't view white space
   216 
   218 
   217         # EOL: Since we are loading/saving ourselves, and the
   219         # EOL: Since we are loading/saving ourselves, and the
   218         # strings will always have \n's in them, set the STC to
   220         # strings will always have \n's in them, set the STC to
   219         # edit them that way.            
   221         # edit them that way.            
   220         self.ConfNodeEditor.SetEOLMode(wx.stc.STC_EOL_LF)
   222         self.PythonCodeEditor.SetEOLMode(wx.stc.STC_EOL_LF)
   221         self.ConfNodeEditor.SetViewEOL(False)
   223         self.PythonCodeEditor.SetViewEOL(False)
   222         
   224         
   223         # No right-edge mode indicator
   225         # No right-edge mode indicator
   224         self.ConfNodeEditor.SetEdgeMode(stc.STC_EDGE_NONE)
   226         self.PythonCodeEditor.SetEdgeMode(stc.STC_EDGE_NONE)
   225         
   227         
   226         self.ConfNodeEditor.SetModEventMask(wx.stc.STC_MOD_BEFOREINSERT|wx.stc.STC_MOD_BEFOREDELETE)
   228         self.PythonCodeEditor.SetModEventMask(wx.stc.STC_MOD_BEFOREINSERT|wx.stc.STC_MOD_BEFOREDELETE)
   227 
   229 
   228         self.ConfNodeEditor.Bind(wx.stc.EVT_STC_DO_DROP, self.OnDoDrop, id=ID_PYTHONEDITOR)
   230         self.PythonCodeEditor.Bind(wx.stc.EVT_STC_DO_DROP, self.OnDoDrop, id=ID_PYTHONEDITOR)
   229         self.ConfNodeEditor.Bind(wx.EVT_KILL_FOCUS, self.OnKillFocus)
   231         self.PythonCodeEditor.Bind(wx.EVT_KILL_FOCUS, self.OnKillFocus)
   230         self.ConfNodeEditor.Bind(wx.stc.EVT_STC_MODIFIED, self.OnModification, id=ID_PYTHONEDITOR)
   232         self.PythonCodeEditor.Bind(wx.stc.EVT_STC_MODIFIED, self.OnModification, id=ID_PYTHONEDITOR)
   231 
   233         
       
   234         return self.PythonCodeEditor
   232 
   235 
   233     def __init__(self, parent, controler, window):
   236     def __init__(self, parent, controler, window):
   234         ConfTreeNodeEditor.__init__(self, parent, controler, window)
   237         ConfTreeNodeEditor.__init__(self, parent, controler, window)
   235         
   238         
   236         self.DisableEvents = False
   239         self.DisableEvents = False
   299     def RefreshView(self):
   302     def RefreshView(self):
   300         ConfTreeNodeEditor.RefreshView(self)
   303         ConfTreeNodeEditor.RefreshView(self)
   301         
   304         
   302         self.ResetBuffer()
   305         self.ResetBuffer()
   303         self.DisableEvents = True
   306         self.DisableEvents = True
   304         old_cursor_pos = self.ConfNodeEditor.GetCurrentPos()
   307         old_cursor_pos = self.PythonCodeEditor.GetCurrentPos()
   305         old_text = self.ConfNodeEditor.GetText()
   308         old_text = self.PythonCodeEditor.GetText()
   306         new_text = self.Controler.GetPythonCode()
   309         new_text = self.Controler.GetPythonCode()
   307         self.ConfNodeEditor.SetText(new_text)
   310         self.PythonCodeEditor.SetText(new_text)
   308         new_cursor_pos = GetCursorPos(old_text, new_text)
   311         new_cursor_pos = GetCursorPos(old_text, new_text)
   309         if new_cursor_pos != None:
   312         if new_cursor_pos != None:
   310             self.ConfNodeEditor.GotoPos(new_cursor_pos)
   313             self.PythonCodeEditor.GotoPos(new_cursor_pos)
   311         else:
   314         else:
   312             self.ConfNodeEditor.GotoPos(old_cursor_pos)
   315             self.PythonCodeEditor.GotoPos(old_cursor_pos)
   313         self.ConfNodeEditor.ScrollToColumn(0)
   316         self.PythonCodeEditor.ScrollToColumn(0)
   314         self.ConfNodeEditor.EmptyUndoBuffer()
   317         self.PythonCodeEditor.EmptyUndoBuffer()
   315         self.DisableEvents = False
   318         self.DisableEvents = False
   316         
   319         
   317         self.ConfNodeEditor.Colourise(0, -1)
   320         self.PythonCodeEditor.Colourise(0, -1)
   318 
   321 
   319     def RefreshModel(self):
   322     def RefreshModel(self):
   320         self.Controler.SetPythonCode(self.ConfNodeEditor.GetText())
   323         self.Controler.SetPythonCode(self.PythonCodeEditor.GetText())
   321 
   324 
   322     def OnKeyPressed(self, event):
   325     def OnKeyPressed(self, event):
   323         if self.ConfNodeEditor.CallTipActive():
   326         if self.PythonCodeEditor.CallTipActive():
   324             self.ConfNodeEditor.CallTipCancel()
   327             self.PythonCodeEditor.CallTipCancel()
   325         key = event.GetKeyCode()
   328         key = event.GetKeyCode()
   326 
   329 
   327         if key == 32 and event.ControlDown():
   330         if key == 32 and event.ControlDown():
   328             pos = self.ConfNodeEditor.GetCurrentPos()
   331             pos = self.PythonCodeEditor.GetCurrentPos()
   329 
   332 
   330             # Code completion
   333             # Code completion
   331             if not event.ShiftDown():
   334             if not event.ShiftDown():
   332                 self.ConfNodeEditor.AutoCompSetIgnoreCase(False)  # so this needs to match
   335                 self.PythonCodeEditor.AutoCompSetIgnoreCase(False)  # so this needs to match
   333 
   336 
   334                 # Images are specified with a appended "?type"
   337                 # Images are specified with a appended "?type"
   335                 self.ConfNodeEditor.AutoCompShow(0, " ".join([word + "?1" for word in keyword.kwlist]))
   338                 self.PythonCodeEditor.AutoCompShow(0, " ".join([word + "?1" for word in keyword.kwlist]))
   336         else:
   339         else:
   337             event.Skip()
   340             event.Skip()
   338 
   341 
   339     def OnKillFocus(self, event):
   342     def OnKillFocus(self, event):
   340         self.ConfNodeEditor.AutoCompCancel()
   343         self.PythonCodeEditor.AutoCompCancel()
   341         event.Skip()
   344         event.Skip()
   342 
   345 
   343     def OnUpdateUI(self, evt):
   346     def OnUpdateUI(self, evt):
   344         # check for matching braces
   347         # check for matching braces
   345         braceAtCaret = -1
   348         braceAtCaret = -1
   346         braceOpposite = -1
   349         braceOpposite = -1
   347         charBefore = None
   350         charBefore = None
   348         caretPos = self.ConfNodeEditor.GetCurrentPos()
   351         caretPos = self.PythonCodeEditor.GetCurrentPos()
   349 
   352 
   350         if caretPos > 0:
   353         if caretPos > 0:
   351             charBefore = self.ConfNodeEditor.GetCharAt(caretPos - 1)
   354             charBefore = self.PythonCodeEditor.GetCharAt(caretPos - 1)
   352             styleBefore = self.ConfNodeEditor.GetStyleAt(caretPos - 1)
   355             styleBefore = self.PythonCodeEditor.GetStyleAt(caretPos - 1)
   353 
   356 
   354         # check before
   357         # check before
   355         if charBefore and chr(charBefore) in "[]{}()" and styleBefore == stc.STC_P_OPERATOR:
   358         if charBefore and chr(charBefore) in "[]{}()" and styleBefore == stc.STC_P_OPERATOR:
   356             braceAtCaret = caretPos - 1
   359             braceAtCaret = caretPos - 1
   357 
   360 
   358         # check after
   361         # check after
   359         if braceAtCaret < 0:
   362         if braceAtCaret < 0:
   360             charAfter = self.ConfNodeEditor.GetCharAt(caretPos)
   363             charAfter = self.PythonCodeEditor.GetCharAt(caretPos)
   361             styleAfter = self.ConfNodeEditor.GetStyleAt(caretPos)
   364             styleAfter = self.PythonCodeEditor.GetStyleAt(caretPos)
   362 
   365 
   363             if charAfter and chr(charAfter) in "[]{}()" and styleAfter == stc.STC_P_OPERATOR:
   366             if charAfter and chr(charAfter) in "[]{}()" and styleAfter == stc.STC_P_OPERATOR:
   364                 braceAtCaret = caretPos
   367                 braceAtCaret = caretPos
   365 
   368 
   366         if braceAtCaret >= 0:
   369         if braceAtCaret >= 0:
   367             braceOpposite = self.ConfNodeEditor.BraceMatch(braceAtCaret)
   370             braceOpposite = self.PythonCodeEditor.BraceMatch(braceAtCaret)
   368 
   371 
   369         if braceAtCaret != -1  and braceOpposite == -1:
   372         if braceAtCaret != -1  and braceOpposite == -1:
   370             self.ConfNodeEditor.BraceBadLight(braceAtCaret)
   373             self.PythonCodeEditor.BraceBadLight(braceAtCaret)
   371         else:
   374         else:
   372             self.ConfNodeEditor.BraceHighlight(braceAtCaret, braceOpposite)
   375             self.PythonCodeEditor.BraceHighlight(braceAtCaret, braceOpposite)
   373 
   376 
   374     def OnMarginClick(self, evt):
   377     def OnMarginClick(self, evt):
   375         # fold and unfold as needed
   378         # fold and unfold as needed
   376         if evt.GetMargin() == 2:
   379         if evt.GetMargin() == 2:
   377             if evt.GetShift() and evt.GetControl():
   380             if evt.GetShift() and evt.GetControl():
   378                 self.FoldAll()
   381                 self.FoldAll()
   379             else:
   382             else:
   380                 lineClicked = self.ConfNodeEditor.LineFromPosition(evt.GetPosition())
   383                 lineClicked = self.PythonCodeEditor.LineFromPosition(evt.GetPosition())
   381 
   384 
   382                 if self.ConfNodeEditor.GetFoldLevel(lineClicked) & stc.STC_FOLDLEVELHEADERFLAG:
   385                 if self.PythonCodeEditor.GetFoldLevel(lineClicked) & stc.STC_FOLDLEVELHEADERFLAG:
   383                     if evt.GetShift():
   386                     if evt.GetShift():
   384                         self.ConfNodeEditor.SetFoldExpanded(lineClicked, True)
   387                         self.PythonCodeEditor.SetFoldExpanded(lineClicked, True)
   385                         self.Expand(lineClicked, True, True, 1)
   388                         self.Expand(lineClicked, True, True, 1)
   386                     elif evt.GetControl():
   389                     elif evt.GetControl():
   387                         if self.ConfNodeEditor.GetFoldExpanded(lineClicked):
   390                         if self.PythonCodeEditor.GetFoldExpanded(lineClicked):
   388                             self.ConfNodeEditor.SetFoldExpanded(lineClicked, False)
   391                             self.PythonCodeEditor.SetFoldExpanded(lineClicked, False)
   389                             self.Expand(lineClicked, False, True, 0)
   392                             self.Expand(lineClicked, False, True, 0)
   390                         else:
   393                         else:
   391                             self.ConfNodeEditor.SetFoldExpanded(lineClicked, True)
   394                             self.PythonCodeEditor.SetFoldExpanded(lineClicked, True)
   392                             self.Expand(lineClicked, True, True, 100)
   395                             self.Expand(lineClicked, True, True, 100)
   393                     else:
   396                     else:
   394                         self.ConfNodeEditor.ToggleFold(lineClicked)
   397                         self.PythonCodeEditor.ToggleFold(lineClicked)
   395 
   398 
   396 
   399 
   397     def FoldAll(self):
   400     def FoldAll(self):
   398         lineCount = self.ConfNodeEditor.GetLineCount()
   401         lineCount = self.PythonCodeEditor.GetLineCount()
   399         expanding = True
   402         expanding = True
   400 
   403 
   401         # find out if we are folding or unfolding
   404         # find out if we are folding or unfolding
   402         for lineNum in range(lineCount):
   405         for lineNum in range(lineCount):
   403             if self.ConfNodeEditor.GetFoldLevel(lineNum) & stc.STC_FOLDLEVELHEADERFLAG:
   406             if self.PythonCodeEditor.GetFoldLevel(lineNum) & stc.STC_FOLDLEVELHEADERFLAG:
   404                 expanding = not self.ConfNodeEditor.GetFoldExpanded(lineNum)
   407                 expanding = not self.PythonCodeEditor.GetFoldExpanded(lineNum)
   405                 break
   408                 break
   406 
   409 
   407         lineNum = 0
   410         lineNum = 0
   408 
   411 
   409         while lineNum < lineCount:
   412         while lineNum < lineCount:
   410             level = self.ConfNodeEditor.GetFoldLevel(lineNum)
   413             level = self.PythonCodeEditor.GetFoldLevel(lineNum)
   411             if level & stc.STC_FOLDLEVELHEADERFLAG and \
   414             if level & stc.STC_FOLDLEVELHEADERFLAG and \
   412                (level & stc.STC_FOLDLEVELNUMBERMASK) == stc.STC_FOLDLEVELBASE:
   415                (level & stc.STC_FOLDLEVELNUMBERMASK) == stc.STC_FOLDLEVELBASE:
   413 
   416 
   414                 if expanding:
   417                 if expanding:
   415                     self.ConfNodeEditor.SetFoldExpanded(lineNum, True)
   418                     self.PythonCodeEditor.SetFoldExpanded(lineNum, True)
   416                     lineNum = self.Expand(lineNum, True)
   419                     lineNum = self.Expand(lineNum, True)
   417                     lineNum = lineNum - 1
   420                     lineNum = lineNum - 1
   418                 else:
   421                 else:
   419                     lastChild = self.ConfNodeEditor.GetLastChild(lineNum, -1)
   422                     lastChild = self.PythonCodeEditor.GetLastChild(lineNum, -1)
   420                     self.ConfNodeEditor.SetFoldExpanded(lineNum, False)
   423                     self.PythonCodeEditor.SetFoldExpanded(lineNum, False)
   421 
   424 
   422                     if lastChild > lineNum:
   425                     if lastChild > lineNum:
   423                         self.ConfNodeEditor.HideLines(lineNum+1, lastChild)
   426                         self.PythonCodeEditor.HideLines(lineNum+1, lastChild)
   424 
   427 
   425             lineNum = lineNum + 1
   428             lineNum = lineNum + 1
   426 
   429 
   427 
   430 
   428 
   431 
   429     def Expand(self, line, doExpand, force=False, visLevels=0, level=-1):
   432     def Expand(self, line, doExpand, force=False, visLevels=0, level=-1):
   430         lastChild = self.ConfNodeEditor.GetLastChild(line, level)
   433         lastChild = self.PythonCodeEditor.GetLastChild(line, level)
   431         line = line + 1
   434         line = line + 1
   432 
   435 
   433         while line <= lastChild:
   436         while line <= lastChild:
   434             if force:
   437             if force:
   435                 if visLevels > 0:
   438                 if visLevels > 0:
   436                     self.ConfNodeEditor.ShowLines(line, line)
   439                     self.PythonCodeEditor.ShowLines(line, line)
   437                 else:
   440                 else:
   438                     self.ConfNodeEditor.HideLines(line, line)
   441                     self.PythonCodeEditor.HideLines(line, line)
   439             else:
   442             else:
   440                 if doExpand:
   443                 if doExpand:
   441                     self.ConfNodeEditor.ShowLines(line, line)
   444                     self.PythonCodeEditor.ShowLines(line, line)
   442 
   445 
   443             if level == -1:
   446             if level == -1:
   444                 level = self.ConfNodeEditor.GetFoldLevel(line)
   447                 level = self.PythonCodeEditor.GetFoldLevel(line)
   445 
   448 
   446             if level & stc.STC_FOLDLEVELHEADERFLAG:
   449             if level & stc.STC_FOLDLEVELHEADERFLAG:
   447                 if force:
   450                 if force:
   448                     if visLevels > 1:
   451                     if visLevels > 1:
   449                         self.ConfNodeEditor.SetFoldExpanded(line, True)
   452                         self.PythonCodeEditor.SetFoldExpanded(line, True)
   450                     else:
   453                     else:
   451                         self.ConfNodeEditor.SetFoldExpanded(line, False)
   454                         self.PythonCodeEditor.SetFoldExpanded(line, False)
   452 
   455 
   453                     line = self.Expand(line, doExpand, force, visLevels-1)
   456                     line = self.Expand(line, doExpand, force, visLevels-1)
   454 
   457 
   455                 else:
   458                 else:
   456                     if doExpand and self.ConfNodeEditor.GetFoldExpanded(line):
   459                     if doExpand and self.PythonCodeEditor.GetFoldExpanded(line):
   457                         line = self.Expand(line, True, force, visLevels-1)
   460                         line = self.Expand(line, True, force, visLevels-1)
   458                     else:
   461                     else:
   459                         line = self.Expand(line, False, force, visLevels-1)
   462                         line = self.Expand(line, False, force, visLevels-1)
   460             else:
   463             else:
   461                 line = line + 1
   464                 line = line + 1
   463         return line
   466         return line
   464 
   467 
   465     def Cut(self):
   468     def Cut(self):
   466         self.ResetBuffer()
   469         self.ResetBuffer()
   467         self.DisableEvents = True
   470         self.DisableEvents = True
   468         self.ConfNodeEditor.CmdKeyExecute(wx.stc.STC_CMD_CUT)
   471         self.PythonCodeEditor.CmdKeyExecute(wx.stc.STC_CMD_CUT)
   469         self.DisableEvents = False
   472         self.DisableEvents = False
   470         self.RefreshModel()
   473         self.RefreshModel()
   471         self.RefreshBuffer()
   474         self.RefreshBuffer()
   472     
   475     
   473     def Copy(self):
   476     def Copy(self):
   474         self.ConfNodeEditor.CmdKeyExecute(wx.stc.STC_CMD_COPY)
   477         self.PythonCodeEditor.CmdKeyExecute(wx.stc.STC_CMD_COPY)
   475     
   478     
   476     def Paste(self):
   479     def Paste(self):
   477         self.ResetBuffer()
   480         self.ResetBuffer()
   478         self.DisableEvents = True
   481         self.DisableEvents = True
   479         self.ConfNodeEditor.CmdKeyExecute(wx.stc.STC_CMD_PASTE)
   482         self.PythonCodeEditor.CmdKeyExecute(wx.stc.STC_CMD_PASTE)
   480         self.DisableEvents = False
   483         self.DisableEvents = False
   481         self.RefreshModel()
   484         self.RefreshModel()
   482         self.RefreshBuffer()
   485         self.RefreshBuffer()