[GRASS-SVN] r55278 - in grass/branches/releasebranch_6_4/gui/wxpython: . gui_core location_wizard

svn_grass at osgeo.org svn_grass at osgeo.org
Sun Mar 3 00:43:13 PST 2013


Author: annakrat
Date: 2013-03-03 00:43:13 -0800 (Sun, 03 Mar 2013)
New Revision: 55278

Modified:
   grass/branches/releasebranch_6_4/gui/wxpython/gis_set.py
   grass/branches/releasebranch_6_4/gui/wxpython/gui_core/dialogs.py
   grass/branches/releasebranch_6_4/gui/wxpython/gui_core/widgets.py
   grass/branches/releasebranch_6_4/gui/wxpython/location_wizard/wizard.py
Log:
wxGUI: check valid mapset/location name on startup page and in wizard

Modified: grass/branches/releasebranch_6_4/gui/wxpython/gis_set.py
===================================================================
--- grass/branches/releasebranch_6_4/gui/wxpython/gis_set.py	2013-03-03 08:41:38 UTC (rev 55277)
+++ grass/branches/releasebranch_6_4/gui/wxpython/gis_set.py	2013-03-03 08:43:13 UTC (rev 55278)
@@ -43,7 +43,11 @@
 from core.gcmd      import GMessage, GError, DecodeString, RunCommand
 from core.utils     import GetListOfLocations, GetListOfMapsets
 from location_wizard.dialogs import RegionDef
+from gui_core.dialogs import TextEntryDialog
+from gui_core.widgets import GenericValidator
 
+from grass.script import core as grass
+
 sys.stderr = codecs.getwriter('utf8')(sys.stderr)
 
 class GRASSStartup(wx.Frame):
@@ -420,10 +424,12 @@
             else:
                 self.SetDefaultRegion(location = gWizard.location)
 
-            dlg = wx.TextEntryDialog(parent=self,
-                                     message=_("Do you want to create new mapset?"),
-                                     caption=_("Create new mapset"),
-                                     defaultValue=self._getDefaultMapsetName())
+            dlg = TextEntryDialog(parent=self,
+                                  message=_("Do you want to create new mapset?"),
+                                  caption=_("Create new mapset"),
+                                  defaultValue=self._getDefaultMapsetName(),
+                                  validator=GenericValidator(grass.legal_name, self._nameValidationFailed))
+
             if dlg.ShowModal() == wx.ID_OK:
                 mapsetName = dlg.GetValue()
                 self.CreateNewMapset(mapsetName)
@@ -515,9 +521,10 @@
                                  'This mapset cannot be renamed.'))
             return
         
-        dlg = wx.TextEntryDialog(parent = self,
-                                 message = _('Current name: %s\n\nEnter new name:') % mapset,
-                                 caption = _('Rename selected mapset'))
+        dlg = TextEntryDialog(parent = self,
+                              message = _('Current name: %s\n\nEnter new name:') % mapset,
+                              caption = _('Rename selected mapset'),
+                              validator = GenericValidator(grass.legal_name, self._nameValidationFailed))
         
         if dlg.ShowModal() ==  wx.ID_OK:
             newmapset = dlg.GetValue()
@@ -550,9 +557,10 @@
         """
         location = self.listOfLocations[self.lblocations.GetSelection()]
 
-        dlg = wx.TextEntryDialog(parent = self,
-                                 message = _('Current name: %s\n\nEnter new name:') % location,
-                                 caption = _('Rename selected location'))
+        dlg = TextEntryDialog(parent = self,
+                              message = _('Current name: %s\n\nEnter new name:') % location,
+                              caption = _('Rename selected location'),
+                              validator = GenericValidator(grass.legal_name, self._nameValidationFailed))
 
         if dlg.ShowModal() ==  wx.ID_OK:
             newlocation = dlg.GetValue()
@@ -781,10 +789,11 @@
     def OnCreateMapset(self, event):
         """!Create new mapset"""
 
-        dlg = wx.TextEntryDialog(parent = self,
+        dlg = TextEntryDialog(parent = self,
                                  message = _('Enter name for new mapset:'),
                                  caption = _('Create new mapset'),
-                                 defaultValue = self._getDefaultMapsetName())
+                                 defaultValue = self._getDefaultMapsetName(),
+                                 validator = GenericValidator(grass.legal_name, self._nameValidationFailed))
 
         if dlg.ShowModal() == wx.ID_OK:
             mapset = dlg.GetValue()
@@ -903,6 +912,12 @@
         event.Skip()
         sys.exit(2)
 
+    def _nameValidationFailed(self, ctrl):
+        message = _("Name <%(name)s> is not a valid name for location or mapset. "
+                    "Please use only ASCII characters excluding %(chars)s "
+                    "and space.") % {'name': ctrl.GetValue(), 'chars': '/"\'@,=*~'}
+        GError(parent=self, message=message, caption=_("Invalid name"))
+
 class GListBox(wx.ListCtrl, listmix.ListCtrlAutoWidthMixin):
     """!Use wx.ListCtrl instead of wx.ListBox, different style for
     non-selectable items (e.g. mapsets with denied permission)"""

Modified: grass/branches/releasebranch_6_4/gui/wxpython/gui_core/dialogs.py
===================================================================
--- grass/branches/releasebranch_6_4/gui/wxpython/gui_core/dialogs.py	2013-03-03 08:41:38 UTC (rev 55277)
+++ grass/branches/releasebranch_6_4/gui/wxpython/gui_core/dialogs.py	2013-03-03 08:43:13 UTC (rev 55278)
@@ -2357,3 +2357,33 @@
         """!Returns currently selected symbol full path.
         """
         return os.path.join(self.symbolPath, self.selectedDir, self.selected)
+
+class TextEntryDialog(wx.Dialog):
+    """!Simple dialog with text field. 
+
+    It differs from wx.TextEntryDialog because it allows adding validator.
+    """
+    def __init__(self, parent, message, caption='',
+                 defaultValue='', pos=wx.DefaultPosition, validator=wx.DefaultValidator):
+        wx.Dialog.__init__(self, parent=parent, id=wx.ID_ANY, title=caption, pos=pos)
+
+        vbox = wx.BoxSizer(wx.VERTICAL)
+
+        stline = wx.StaticText(self, id=wx.ID_ANY, label=message)
+        vbox.Add(item=stline, proportion=0, flag=wx.EXPAND | wx.ALL, border=10)
+
+        self._textCtrl = wx.TextCtrl(self, id=wx.ID_ANY, size = (300, -1),
+                                     value=defaultValue, validator=validator)
+        vbox.Add(item=self._textCtrl, proportion=0, flag=wx.EXPAND | wx.LEFT | wx.RIGHT, border=10)
+        self._textCtrl.SetFocus()
+
+        sizer = self.CreateSeparatedButtonSizer(wx.CANCEL | wx.OK)
+        vbox.Add(item=sizer, proportion=1, flag=wx.EXPAND | wx.ALL, border=10)
+
+        self.SetSizerAndFit(vbox)
+        
+    def GetValue(self):
+        return self._textCtrl.GetValue()
+
+    def SetValue(self, value):
+        self._textCtrl.SetValue(value)

Modified: grass/branches/releasebranch_6_4/gui/wxpython/gui_core/widgets.py
===================================================================
--- grass/branches/releasebranch_6_4/gui/wxpython/gui_core/widgets.py	2013-03-03 08:41:38 UTC (rev 55277)
+++ grass/branches/releasebranch_6_4/gui/wxpython/gui_core/widgets.py	2013-03-03 08:43:13 UTC (rev 55278)
@@ -335,7 +335,52 @@
         # Returning without calling even.Skip eats the event before it
         # gets to the text control
         return  
-    
+
+
+class GenericValidator(wx.PyValidator):
+    """ This validator checks condition and calls callback
+    in case the condition is not fulfilled.
+    """
+    def __init__(self, condition, callback):
+        """ Standard constructor.
+
+        @param condition function which accepts string value and returns T/F
+        @param callback function which is called when condition is not fulfilled
+        """
+        wx.PyValidator.__init__(self)
+        self._condition = condition
+        self._callback = callback
+
+    def Clone(self):
+        """ Standard cloner.
+
+        Note that every validator must implement the Clone() method.
+        """
+        return GenericValidator(self._condition, self._callback)
+
+    def Validate(self, win):
+        """ Validate the contents of the given text control.
+        """
+        ctrl = self.GetWindow()
+        text = ctrl.GetValue()
+        if not self._condition(text):
+            self._callback(ctrl)
+            return False
+        else:
+            return True
+
+    def TransferToWindow(self):
+        """ Transfer data from validator to window.
+        """
+        return True # Prevent wxDialog from complaining.
+
+
+    def TransferFromWindow(self):
+        """ Transfer data from window to validator.
+        """
+        return True # Prevent wxDialog from complaining.
+
+
 class ItemTree(CT.CustomTreeCtrl):
     def __init__(self, parent, id = wx.ID_ANY,
                  ctstyle = CT.TR_HIDE_ROOT | CT.TR_FULL_ROW_HIGHLIGHT | CT.TR_HAS_BUTTONS |

Modified: grass/branches/releasebranch_6_4/gui/wxpython/location_wizard/wizard.py
===================================================================
--- grass/branches/releasebranch_6_4/gui/wxpython/location_wizard/wizard.py	2013-03-03 08:41:38 UTC (rev 55277)
+++ grass/branches/releasebranch_6_4/gui/wxpython/location_wizard/wizard.py	2013-03-03 08:43:13 UTC (rev 55278)
@@ -42,6 +42,7 @@
 from core                    import utils
 from core.gcmd               import RunCommand, GError, GMessage, GWarning
 from gui_core.ghelp          import HelpFrame
+from gui_core.widgets        import GenericValidator
 from location_wizard.base    import BaseClass
 from location_wizard.dialogs import SelectTransformDialog
 
@@ -102,6 +103,7 @@
         # text controls
         self.tgisdbase = self.MakeTextCtrl(grassdatabase, size = (300, -1))
         self.tlocation = self.MakeTextCtrl("newLocation", size = (300, -1))
+        self.tlocation.SetValidator(GenericValidator(grass.legal_name, self._nameValidationFailed))
         self.tlocTitle = self.MakeTextCtrl(size = (400, -1))
         
         # layout
@@ -153,6 +155,12 @@
         self.tgisdbase.Bind(wx.EVT_TEXT,        self.OnChangeName)
         self.tlocation.Bind(wx.EVT_TEXT,        self.OnChangeName)
         
+    def _nameValidationFailed(self, ctrl):
+        message = _("Name <%(name)s> is not a valid name for location. "
+                    "Please use only ASCII characters excluding %(chars)s "
+                    "and space.") % {'name': ctrl.GetValue(), 'chars': '/"\'@,=*~'}
+        GError(parent=self, message=message, caption=_("Invalid location name"))
+
     def OnChangeName(self, event):
         """!Name for new location was changed"""
         nextButton = wx.FindWindowById(wx.ID_FORWARD)



More information about the grass-commit mailing list