Laurent@1091: #!/usr/bin/env python
Laurent@1091: # -*- coding: utf-8 -*-
Laurent@1091: 
andrej@1511: # This file is part of Beremiz, a Integrated Development Environment for
andrej@1511: # programming IEC 61131-3 automates supporting plcopen standard and CanFestival.
andrej@1511: #
andrej@1511: # Copyright (C) 2007: Edouard TISSERANT and Laurent BESSARD
andrej@1511: #
andrej@1511: # See COPYING file for copyrights details.
andrej@1511: #
andrej@1511: # This program is free software; you can redistribute it and/or
andrej@1511: # modify it under the terms of the GNU General Public License
andrej@1511: # as published by the Free Software Foundation; either version 2
andrej@1511: # of the License, or (at your option) any later version.
andrej@1511: #
andrej@1511: # This program is distributed in the hope that it will be useful,
andrej@1511: # but WITHOUT ANY WARRANTY; without even the implied warranty of
andrej@1511: # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
andrej@1511: # GNU General Public License for more details.
andrej@1511: #
andrej@1511: # You should have received a copy of the GNU General Public License
andrej@1511: # along with this program; if not, write to the Free Software
andrej@1511: # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.
andrej@1511: 
andrej@1881: 
andrej@1881: from __future__ import absolute_import
andrej@2456: from functools import reduce
Laurent@1091: import wx
Laurent@1091: import wx.stc
andrej@2432: from six.moves import xrange
Laurent@1091: 
Laurent@1091: if wx.Platform == '__WXMSW__':
andrej@1747:     faces = {
andrej@1747:         'times': 'Times New Roman',
andrej@1747:         'mono':  'Courier New',
andrej@1747:         'helv':  'Arial',
andrej@1747:         'other': 'Comic Sans MS',
andrej@1747:         'size':  10,
andrej@1747:     }
Laurent@1091: else:
andrej@1747:     faces = {
andrej@1747:         'times': 'Times',
edouard@2918:         'mono':  'FreeMono',
andrej@1747:         'helv':  'Helvetica',
andrej@1747:         'other': 'new century schoolbook',
andrej@1747:         'size':  12,
andrej@1747:     }
Laurent@1091: 
Laurent@1104: NAVIGATION_KEYS = [
Laurent@1104:     wx.WXK_END,
Laurent@1104:     wx.WXK_HOME,
Laurent@1104:     wx.WXK_LEFT,
Laurent@1104:     wx.WXK_UP,
Laurent@1104:     wx.WXK_RIGHT,
Laurent@1104:     wx.WXK_DOWN,
Laurent@1104:     wx.WXK_PAGEUP,
Laurent@1104:     wx.WXK_PAGEDOWN,
Laurent@1104:     wx.WXK_NUMPAD_HOME,
Laurent@1104:     wx.WXK_NUMPAD_LEFT,
Laurent@1104:     wx.WXK_NUMPAD_UP,
Laurent@1104:     wx.WXK_NUMPAD_RIGHT,
Laurent@1104:     wx.WXK_NUMPAD_DOWN,
Laurent@1104:     wx.WXK_NUMPAD_PAGEUP,
Laurent@1104:     wx.WXK_NUMPAD_PAGEDOWN,
Laurent@1104:     wx.WXK_NUMPAD_END]
Laurent@1104: 
andrej@1736: 
Laurent@1091: def GetCursorPos(old, new):
Laurent@1091:     if old == "":
Laurent@1091:         return 0
Laurent@1091:     old_length = len(old)
Laurent@1091:     new_length = len(new)
Laurent@1091:     common_length = min(old_length, new_length)
Laurent@1091:     i = 0
Laurent@1091:     for i in xrange(common_length):
Laurent@1091:         if old[i] != new[i]:
Laurent@1091:             break
Laurent@1091:     if old_length < new_length:
Laurent@1091:         if common_length > 0 and old[i] != new[i]:
Laurent@1091:             return i + new_length - old_length
Laurent@1091:         else:
Laurent@1091:             return i + new_length - old_length + 1
Laurent@1091:     elif old_length > new_length or i < min(old_length, new_length) - 1:
Laurent@1091:         if common_length > 0 and old[i] != new[i]:
Laurent@1091:             return i
Laurent@1091:         else:
Laurent@1091:             return i + 1
Laurent@1091:     else:
Laurent@1091:         return None
Laurent@1091: 
andrej@1736: 
Laurent@1091: class CustomStyledTextCtrl(wx.stc.StyledTextCtrl):
andrej@1735: 
Laurent@1091:     def __init__(self, *args, **kwargs):
Laurent@1092:         wx.stc.StyledTextCtrl.__init__(self, *args, **kwargs)
andrej@1735: 
Laurent@1091:         self.Bind(wx.EVT_MOTION, self.OnMotion)
andrej@1735: 
Laurent@1091:     def OnMotion(self, event):
Laurent@1091:         if wx.Platform == '__WXMSW__':
Laurent@1091:             if not event.Dragging():
andrej@1847:                 x, _y = event.GetPosition()
Laurent@1091:                 margin_width = reduce(
andrej@1878:                     lambda x, y: x + y,
andrej@1878:                     [self.GetMarginWidth(i) for i in xrange(3)],
andrej@1878:                     0)
Laurent@1091:                 if x <= margin_width:
Laurent@1092:                     self.SetCursor(wx.StockCursor(wx.CURSOR_ARROW))
Laurent@1091:                 else:
Laurent@1092:                     self.SetCursor(wx.StockCursor(wx.CURSOR_IBEAM))
Laurent@1092:             else:
Laurent@1092:                 event.Skip()
Laurent@1091:         else:
Laurent@1091:             event.Skip()
Laurent@1091: 
Laurent@1091:     def AppendText(self, text):
Laurent@1092:         self.GotoPos(self.GetLength())
Laurent@1091:         self.AddText(text)