# Copyright (C) 2009, 2010, 2011, 2012, 2013, 2014, 2015, 2016, 2017, 2018 Rickard Lindberg, Roger Lindberg
#
# This file is part of Timeline.
#
# Timeline is free software: you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
# the Free Software Foundation, either version 3 of the License, or
# (at your option) any later version.
#
# Timeline is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with Timeline. If not, see <http://www.gnu.org/licenses/>.
import humblewx
import wx
[docs]class TextPatternControlController(humblewx.Controller):
[docs] def on_init(self):
self.separators = []
self.last_selected_group = None
self.validator = None
self.up_handlers = {}
self.down_handlers = {}
[docs] def on_after_set_focus(self):
pass
[docs] def on_kill_focus(self, event):
self.last_selected_group = self.get_selected_group()
self.view.SetSelection(0, 0)
event.Skip()
[docs] def on_left_double_click(self, evt):
self._select_group(self.get_selected_group())
[docs] def on_text(self, event):
self.validate()
[docs] def on_char(self, event):
skip = True
if event.GetKeyCode() == wx.WXK_TAB:
if event.ShiftDown():
skip = self.on_shift_tab()
flag = wx.NavigationKeyEvent.IsBackward
else:
skip = self.on_tab()
flag = wx.NavigationKeyEvent.IsForward
if skip:
event.EventObject.Navigate(flags=flag)
skip = False
elif (event.GetKeyCode() == wx.WXK_UP and
self.view.GetSelectedGroup() in self.up_handlers and
self._is_text_valid()):
self.up_handlers[self.view.GetSelectedGroup()]()
skip = False
elif (event.GetKeyCode() == wx.WXK_DOWN and
self.view.GetSelectedGroup() in self.down_handlers and
self._is_text_valid()):
self.down_handlers[self.view.GetSelectedGroup()]()
skip = False
event.Skip(skip)
[docs] def on_tab(self):
return not self._select_group(self.get_selected_group() + 1)
[docs] def on_shift_tab(self):
return not self._select_group(self.get_selected_group() - 1)
[docs] def get_parts(self):
if self._get_groups() is not None:
return [value for (value, _, _) in self._get_groups()]
return None
[docs] def get_selected_group(self):
(selection_start, _) = self.view.GetSelection()
if self._get_groups() is not None:
for (index, (_, start, end)) in enumerate(self._get_groups()):
if start <= selection_start <= end:
return index
return 0
[docs] def set_separators(self, separators):
self.separators = separators
self.validate()
[docs] def set_parts(self, parts):
(start, end) = self.view.GetSelection()
text = ""
for (index, value) in enumerate(parts):
if index > 0:
text += self.separators[index-1]
text += value
self.view.SetValue(text)
self.validate()
self.view.SetSelection(start, end)
[docs] def set_validator(self, validator):
self.validator = validator
self.validate()
[docs] def set_up_handler(self, group, up_handler):
self.up_handlers[group] = up_handler
[docs] def set_down_handler(self, group, down_handler):
self.down_handlers[group] = down_handler
[docs] def validate(self):
if self._is_text_valid():
self.view.SetBackgroundColour(wx.NullColour)
else:
self.view.SetBackgroundColour("pink")
self.view.Refresh()
def _get_groups(self):
text = self.view.GetValue()
groups = []
start = 0
for separator in self.separators:
separator_pos = text[start:].find(separator)
if separator_pos == -1:
return None
groups.append(self._extract_section(start, start+separator_pos))
start += separator_pos + len(separator)
groups.append(self._extract_section(start, len(text)))
return groups
def _extract_section(self, start, end):
return self.view.GetValue()[start:end], start, end
def _is_text_valid(self):
if self.get_parts() is None:
return False
elif self.validator is None:
return True
else:
return self.validator()
def _select_group(self, section_to_focus):
if self._get_groups() is not None:
for (index, (_, start, end)) in enumerate(self._get_groups()):
if index == section_to_focus:
self.view.SetSelection(start, end)
return True
return False