2 @package gmodeler.model 
    4 @brief wxGUI Graphical Modeler (base classes & read/write) 
   11  - model::ModelRelation 
   14  - model::ModelCondition 
   15  - model::ProcessModelFile 
   16  - model::WriteModelFile 
   17  - model::WritePythonFile 
   18  - model::ModelParamDialog 
   20 (C) 2010-2012 by the GRASS Development Team 
   22 This program is free software under the GNU General Public License 
   23 (>=v2). Read the file COPYING that comes with GRASS for details. 
   25 @author Martin Landa <landa.martin gmail.com> 
   35     import xml.etree.ElementTree 
as etree
 
   37     import elementtree.ElementTree 
as etree 
 
   40 from wx.lib 
import ogl
 
   42 from core                
import globalvar
 
   43 from core                
import utils
 
   44 from core.gcmd           import GMessage, GException, GError, RunCommand, EncodeString, GWarning, GetDefaultEncoding
 
   46 from gui_core.forms      
import GUI, CmdPanel
 
   53     """!Class representing the model""" 
   59                             'description' : _(
"Script generated by wxGUI Graphical Modeler."),
 
   60                             'author'      : getpass.getuser() }
 
   68         """!Get canvas or None""" 
   72         """!Get list of model items 
   74         @param objType Object type to filter model objects 
   80         for item 
in self.
items:
 
   81             if isinstance(item, objType):
 
   87         """!Get item of given id 
   91         @return Model* instance 
   92         @return None if no item found 
   96             if item.GetId() == aId:
 
  102         """!Get number of items""" 
  104             return len(self.
GetItems(objType = ModelAction))
 
  109         """!Get next id (data ignored) 
  111         @return next id to be used (default: 1) 
  113         if len(self.
items) < 1:
 
  116         currId = self.
items[-1].GetId()
 
  123         """!Get model properties""" 
  127         """!Get model variables""" 
  134         """!Set model variables""" 
  142         """!Remove item from model 
  144         @return list of related items to remove/update 
  149         if not isinstance(item, ModelData):
 
  150             self.items.remove(item)
 
  152         if isinstance(item, ModelAction):
 
  153             for rel 
in item.GetRelations():
 
  156                 if len(data.GetRelations()) < 2:
 
  161         elif isinstance(item, ModelData):
 
  162             for rel 
in item.GetRelations():
 
  164                 if rel.GetFrom() == self:
 
  165                     relList.append(rel.GetTo())
 
  167                     relList.append(rel.GetFrom())
 
  169         elif isinstance(item, ModelLoop):
 
  170             for rel 
in item.GetRelations():
 
  173                 action.UnSetBlock(item)
 
  175         return relList, upList
 
  178         """!Find action by id""" 
  179         alist = self.
GetItems(objType = ModelAction)
 
  181             if action.GetId() == aId:
 
  187         """!Get list of data items""" 
  189         dataItems = self.
GetItems(objType = ModelData)
 
  191         for action 
in self.
GetItems(objType = ModelAction):
 
  192             for rel 
in action.GetRelations():
 
  193                 dataItem = rel.GetData()
 
  194                 if dataItem 
not in result:
 
  195                     result.append(dataItem)
 
  196                 if dataItem 
in dataItems:
 
  197                     dataItems.remove(dataItem)
 
  206         """!Find data item in the model 
  211         @return ModelData instance 
  212         @return None if not found 
  215             if data.GetValue() == value 
and \
 
  216                     data.GetPrompt() == prompt:
 
  222         """!Load model definition stored in GRASS Model XML file (gxm) 
  224         @todo Validate against DTD 
  226         Raise exception on error. 
  228         dtdFilename = os.path.join(globalvar.ETCWXDIR, 
"xml", 
"grass-gxm.dtd")
 
  233         except StandardError, e:
 
  237             win = self.canvas.parent
 
  239                 win.SetPosition(gxmXml.pos)
 
  241                 win.SetSize(gxmXml.size)
 
  248         for action 
in gxmXml.actions:
 
  250                                      x = action[
'pos'][0],
 
  251                                      y = action[
'pos'][1],
 
  252                                      width = action[
'size'][0],
 
  253                                      height = action[
'size'][1],
 
  254                                      task = action[
'task'],
 
  257             if action[
'disabled']:
 
  258                 actionItem.Enable(
False)
 
  262             actionItem.SetValid(actionItem.GetTask().get_options())
 
  266         for data 
in gxmXml.data:
 
  270                                  width = data[
'size'][0],
 
  271                                  height = data[
'size'][1],
 
  272                                  prompt = data[
'prompt'],
 
  273                                  value = data[
'value'])
 
  274             dataItem.SetIntermediate(data[
'intermediate'])
 
  276             for rel 
in data[
'rels']:
 
  278                 if rel[
'dir'] == 
'from':
 
  279                     relation = 
ModelRelation(parent = self, fromShape = dataItem,
 
  280                                              toShape = actionItem, param = rel[
'name'])
 
  282                     relation = 
ModelRelation(parent = self, fromShape = actionItem,
 
  283                                              toShape = dataItem, param = rel[
'name'])
 
  284                 relation.SetControlPoints(rel[
'points'])
 
  285                 actionItem.AddRelation(relation)
 
  286                 dataItem.AddRelation(relation)
 
  292         for loop 
in gxmXml.loops:
 
  296                                  width = loop[
'size'][0],
 
  297                                  height = loop[
'size'][1],
 
  303         for condition 
in gxmXml.conditions:
 
  305                                            x = condition[
'pos'][0],
 
  306                                            y = condition[
'pos'][1],
 
  307                                            width = condition[
'size'][0],
 
  308                                            height = condition[
'size'][1],
 
  309                                            text = condition[
'text'],
 
  310                                            id = condition[
'id'])
 
  314         for loop 
in gxmXml.loops:
 
  316             for aId 
in loop[
'items']:
 
  320             loopItem = self.
GetItem(loop[
'id'])
 
  321             loopItem.SetItems(alist)
 
  323             for action 
in loopItem.GetItems():
 
  324                 action.SetBlock(loopItem)
 
  326         for condition 
in gxmXml.conditions:
 
  327             conditionItem = self.
GetItem(condition[
'id'])
 
  328             for b 
in condition[
'items'].keys():
 
  330                 for aId 
in condition[
'items'][b]:
 
  333                 conditionItem.SetItems(alist, branch = b)
 
  335             items = conditionItem.GetItems()
 
  336             for b 
in items.keys():
 
  337                 for action 
in items[b]:
 
  338                     action.SetBlock(conditionItem)
 
  341         """!Add item to the list""" 
  342         iId = newItem.GetId()
 
  345         for item 
in self.
items:
 
  346             if item.GetId() > iId:
 
  347                 self.items.insert(i, newItem)
 
  351         self.items.append(newItem)
 
  354         """Return True if model is valid""" 
  361         """!Validate model, return None if model is valid otherwise 
  366         pattern = re.compile(
r'(.*)(%.+\s?)(.*)')
 
  367         for action 
in self.
GetItems(objType = ModelAction):
 
  368             cmd = action.GetLog(string = 
False)
 
  370             task = GUI(show = 
None).ParseCommand(cmd = cmd)
 
  371             errList += map(
lambda x: cmd[0] + 
': ' + x, task.get_cmd_error())
 
  377                 key, value = opt.split(
'=', 1)
 
  378                 sval = pattern.search(value)
 
  380                     var = sval.group(2).strip()[1:] 
 
  381                     if var 
not in variables:
 
  383                         for item 
in filter(
lambda x: isinstance(x, ModelLoop), action.GetBlock()):
 
  384                             if var 
in item.GetText():
 
  388                             errList.append(cmd[0] + 
": " + _(
"undefined variable '%s'") % var)
 
  394     def _substituteFile(self, item, params = None, checkOnly = False):
 
  395         """!Subsitute variables in command file inputs 
  397         @param checkOnly tuble - True to check variable, don't touch files 
  399         @return list of undefined variables 
  406         for p 
in item.GetParams()[
'params']:
 
  407             if p.get(
'element', 
'') == 
'file' and \
 
  408                     p.get(
'prompt', 
'') == 
'input' and \
 
  409                     p.get(
'age', 
'') == 
'old_file':
 
  410                 filename = p.get(
'value', p.get(
'default', 
''))
 
  412                         mimetypes.guess_type(filename)[0] == 
'text/plain':
 
  417             fd = open(finput, 
"r") 
  419                 data = self.
fileInput[finput] = fd.read()
 
  426             for variable 
in variables:
 
  427                 pattern = re.compile(
'%' + variable)
 
  429                 if params 
and 'variables' in params:
 
  430                     for p 
in params[
'variables'][
'params']:
 
  431                         if variable == p.get(
'name', 
''):
 
  432                             if p.get(
'type', 
'string') == 
'string':
 
  433                                 value = p.get(
'value', 
'')
 
  435                                 value = str(p.get(
'value', 
''))
 
  439                     value = variables[variable].get(
'value', 
'')
 
  441                 data = pattern.sub(value, data)
 
  445             pattern = re.compile(
r'(.*)(%.+\s?)(.*)')
 
  446             sval = pattern.search(data)
 
  448                 var = sval.group(2).strip()[1:] 
 
  449                 cmd = item.GetLog(string = 
False)[0]
 
  450                 errList.append(cmd + 
": " + _(
"undefined variable '%s'") % var)
 
  454                     fd = open(finput, 
"w")
 
  467     def RunAction(self, item, params, log, onDone, onPrepare = None, statusbar = None):
 
  470         @param item action item 
  471         @param params parameters dict 
  472         @param log logging window 
  473         @param onDone on-done method 
  474         @param onPrepare on-prepare method 
  475         @param statusbar wx.StatusBar instance or None 
  477         name = item.GetName()
 
  479             paramsOrig = item.GetParams(dcopy = 
True)
 
  480             item.MergeParams(params[name])
 
  483             statusbar.SetStatusText(_(
'Running model...'), 0)
 
  485         data = { 
'item' : item,
 
  486                  'params' : copy.deepcopy(params) }
 
  487         log.RunCmd(command = item.GetLog(string = 
False, substitute = params),
 
  488                    onDone = onDone, onPrepare = self.
OnPrepare, userData = data)
 
  491             item.SetParams(paramsOrig)
 
  493     def Run(self, log, onDone, parent = None):
 
  496         @param log logging window (see goutput.GMConsole) 
  497         @param onDone on-done method 
  498         @param parent window for messages or None 
  501             GMessage(parent = parent,
 
  502                      message = _(
'Model is empty. Nothing to run.'))
 
  506         if isinstance(parent, wx.Frame):
 
  507             statusbar = parent.GetStatusBar()
 
  511             statusbar.SetStatusText(_(
'Validating model...'), 0)
 
  514             statusbar.SetStatusText(
'', 0)
 
  516             dlg = wx.MessageDialog(parent = parent,
 
  517                                    message = _(
'Model is not valid. Do you want to ' 
  518                                                'run the model anyway?\n\n%s') % 
'\n'.join(errList),
 
  519                                    caption = _(
"Run model?"),
 
  520                                    style = wx.YES_NO | wx.NO_DEFAULT |
 
  521                                    wx.ICON_QUESTION | wx.CENTRE)
 
  522             ret = dlg.ShowModal()
 
  535             ret = dlg.ShowModal()
 
  540             err = dlg.GetErrors()
 
  541             delInterData = dlg.DeleteIntermediateData()
 
  544                 GError(parent = parent, message = unicode(
'\n'.join(err)))
 
  548             for key, item 
in params.iteritems():
 
  549                 for p 
in item[
'params']:
 
  550                     if p.get(
'value', 
'') == 
'':
 
  551                         err.append((key, p.get(
'name', 
''), p.get(
'description', 
'')))
 
  553                 GError(parent = parent,
 
  554                        message = _(
"Variables below not defined:") + \
 
  555                            "\n\n" + unicode(
'\n'.join(map(
lambda x: 
"%s: %s (%s)" % (x[0], x[1], x[2]), err))))
 
  558         log.cmdThread.SetId(-1)
 
  560             if not item.IsEnabled():
 
  562             if isinstance(item, ModelAction):
 
  563                 if item.GetBlockId():
 
  565                 self.
RunAction(item, params, log, onDone)
 
  566             elif isinstance(item, ModelLoop):
 
  567                 cond = item.GetText()
 
  570                 for variable 
in variables:
 
  571                     pattern = re.compile(
'%' + variable)
 
  572                     if pattern.search(cond):
 
  574                         if params 
and 'variables' in params:
 
  575                             for p 
in params[
'variables'][
'params']:
 
  576                                 if variable == p.get(
'name', 
''):
 
  577                                     value = p.get(
'value', 
'')
 
  581                             value = variables[variable].get(
'value', 
'')
 
  586                         vtype = variables[variable].get(
'type', 
'string')
 
  587                         if vtype == 
'string':
 
  588                             value = 
'"' + value + 
'"' 
  589                         cond = pattern.sub(value, cond)
 
  592                 condVar, condText = map(
lambda x: x.strip(), re.split(
'\s*in\s*', cond))
 
  593                 pattern = re.compile(
'%' + condVar)
 
  595                 if condText[0] == 
'`' and condText[-1] == 
'`':
 
  602                         vlist = ret.splitlines()
 
  604                     vlist = eval(condText)
 
  606                 if 'variables' not in params:
 
  607                     params[
'variables'] = { 
'params' : [] }
 
  608                 varDict = { 
'name' : condVar, 
'value' : 
'' }
 
  609                 params[
'variables'][
'params'].append(varDict)
 
  612                     for action 
in item.GetItems():
 
  613                         if not isinstance(action, ModelAction) 
or \
 
  614                                 not action.IsEnabled():
 
  617                         varDict[
'value'] = var
 
  619                         self.
RunAction(item = action, params = params,
 
  620                                        log = log, onDone = onDone)
 
  621                 params[
'variables'][
'params'].remove(varDict)
 
  628             for item 
in params.itervalues():
 
  629                 for p 
in item[
'params']:
 
  633         """!Detele intermediate data""" 
  637             log.RunCmd([
'g.remove', 
'rast=%s' %
','.join(rast)])
 
  639             log.RunCmd([
'g.remove', 
'rast3d=%s' %
','.join(rast3d)])
 
  641             log.RunCmd([
'g.remove', 
'vect=%s' %
','.join(vect)])
 
  644         """!Get info about intermediate data""" 
  649             if not data.IsIntermediate():
 
  651             name = data.GetValue()
 
  652             prompt = data.GetPrompt()
 
  653             if prompt == 
'raster':
 
  655             elif prompt == 
'vector':
 
  657             elif prompt == 
'rast3d':
 
  662             msg += 
'\n\n%s: ' % _(
'Raster maps')
 
  663             msg += 
', '.join(rast)
 
  665             msg += 
'\n\n%s: ' % _(
'3D raster maps')
 
  666             msg += 
', '.join(rast3d)
 
  668             msg += 
'\n\n%s: ' % _(
'Vector maps')
 
  669             msg += 
', '.join(vect)
 
  671         return rast, vect, rast3d, msg
 
  675         for item 
in self.
items:
 
  679         """!Return True if model is parameterized""" 
  686         """!Return parameterized options""" 
  691             result[
"variables"] = { 
'flags'  : list(),
 
  694             for name, values 
in self.variables.iteritems():
 
  695                 gtype = values.get(
'type', 
'string')
 
  696                 if gtype 
in (
'raster', 
'vector', 
'mapset', 
'file'):
 
  699                     if gtype == 
'raster':
 
  709                 params.append({ 
'gisprompt' : gisprompt,
 
  711                                 'description' : values.get(
'description', 
''),
 
  712                                 'guidependency' : 
'',
 
  716                                 'value' : values.get(
'value', 
''),
 
  721                                 'parameterized' : 
False,
 
  722                                 'values_desc' : list(),
 
  730         for action 
in self.
GetItems(objType = ModelAction):
 
  731             if not action.IsEnabled():
 
  733             name   = action.GetName()
 
  734             params = action.GetParams()
 
  735             for f 
in params[
'flags']:
 
  736                 if f.get(
'parameterized', 
False):
 
  737                     if name 
not in result:
 
  738                         result[name] = { 
'flags' : list(),
 
  741                     result[name][
'flags'].append(f)
 
  742             for p 
in params[
'params']:
 
  743                 if p.get(
'parameterized', 
False):
 
  744                     if name 
not in result:
 
  745                         result[name] = { 
'flags' : list(),
 
  748                     result[name][
'params'].append(p)
 
  772         """!Record new relation 
  774         self.rels.append(rel)
 
  777         """!Get list of relations 
  779         @param fdir True for 'from' 
  785         for rel 
in self.
rels:
 
  787                 if rel.GetFrom() == self:
 
  790                 if rel.GetTo() == self:
 
  796         """!Get True if action is enabled, otherwise False""" 
  800         """!Enable/disable action""" 
  808         """!Add object to the block (loop/condition) 
  810         @param item reference to ModelLoop or ModelCondition which 
  811         defines loops/condition 
  813         if item 
not in self.inBlock:
 
  814             self.inBlock.append(item)
 
  817         """!Remove object from the block (loop/consition) 
  819         @param item reference to ModelLoop or ModelCondition which 
  820         defines loops/codition 
  823             self.inBlock.remove(item)
 
  826         """!Get list of related ModelObject(s) which defines block 
  829         @return list of ModelObjects 
  834         """!Get list of related ids which defines block 
  840             ret.append(mo.GetId())
 
  845     """!Action class (GRASS module)""" 
  846     def __init__(self, parent, x, y, id = -1, cmd = None, task = None, width = None, height = None):
 
  847         ModelObject.__init__(self, id)
 
  853             width = UserSettings.Get(group=
'modeler', key=
'action', subkey=(
'size', 
'width'))
 
  855             height = UserSettings.Get(group=
'modeler', key=
'action', subkey=(
'size', 
'height'))
 
  857         if cmd 
and cmd[0] 
in (
'r.mapcalc', 
'v.type'):
 
  861             self.
task = GUI(show = 
None).ParseCommand(cmd = cmd)
 
  875         if self.parent.GetCanvas():
 
  876             ogl.RectangleShape.__init__(self, width, height)
 
  878             self.SetCanvas(self.
parent)
 
  881             self.SetPen(wx.BLACK_PEN)
 
  887             self.
SetValid(self.task.get_options())
 
  889     def _setBrush(self, running = False):
 
  892             color = UserSettings.Get(group=
'modeler', key=
'action',
 
  893                                      subkey=(
'color', 
'running'))
 
  895             color = UserSettings.Get(group=
'modeler', key=
'disabled',
 
  898             color = UserSettings.Get(group=
'modeler', key=
'action',
 
  899                                      subkey=(
'color', 
'valid'))
 
  901             color = UserSettings.Get(group=
'modeler', key=
'action',
 
  902                                      subkey=(
'color', 
'invalid'))
 
  904         wxColor = wx.Colour(color[0], color[1], color[2])
 
  905         self.SetBrush(wx.Brush(wxColor))
 
  910             width = int(UserSettings.Get(group=
'modeler', key=
'action',
 
  911                                          subkey=(
'width', 
'parameterized')))
 
  913             width = int(UserSettings.Get(group=
'modeler', key=
'action',
 
  914                                          subkey=(
'width', 
'default')))
 
  922         cmd = self.task.get_cmd(ignoreErrors = 
True)
 
  923         if cmd 
and len(cmd) > 0:
 
  925             self.AddText(
'(%d) %s' % (self.
id, cmd[0]))
 
  927             self.AddText(
'(%d) <<%s>>' % (self.
id, _(
"unknown")))
 
  930         """!Record properties dialog""" 
  931         self.task.params = params[
'params']
 
  932         self.task.flags  = params[
'flags']
 
  936         """!Get properties dialog""" 
  939     def GetLog(self, string = True, substitute = None):
 
  942         @param string True to get cmd as a string otherwise a list 
  943         @param substitute dictionary of parameter to substitute or None 
  945         cmd = self.task.get_cmd(ignoreErrors = 
True, ignoreRequired = 
True,
 
  946                                 ignoreDefault = 
False)
 
  951             if 'variables' in substitute:
 
  952                 for p 
in substitute[
'variables'][
'params']:
 
  953                     variables.append(p.get(
'name', 
''))
 
  955                 variables = self.parent.GetVariables()
 
  956             for variable 
in variables:
 
  957                 pattern= re.compile(
'%' + variable)
 
  959                 if substitute 
and 'variables' in substitute:
 
  960                     for p 
in substitute[
'variables'][
'params']:
 
  961                         if variable == p.get(
'name', 
''):
 
  962                             if p.get(
'type', 
'string') == 
'string':
 
  963                                 value = p.get(
'value', 
'')
 
  965                                 value = str(p.get(
'value', 
''))
 
  969                     value = variables[variable].get(
'value', 
'')
 
  974                 for idx 
in range(len(cmd)):
 
  975                     if pattern.search(cmd[idx]):
 
  976                         cmd[idx] = pattern.sub(value, cmd[idx])
 
  990         cmd = self.task.get_cmd(ignoreErrors = 
True)
 
  991         if cmd 
and len(cmd) > 0:
 
  997         """!Get dictionary of parameters""" 
  999             return copy.deepcopy(self.task.get_options())
 
 1001         return self.task.get_options()
 
 1004         """!Get grassTask instance""" 
 1008         """!Set dictionary of parameters""" 
 1009         self.task.params = params[
'params']
 
 1010         self.task.flags  = params[
'flags']
 
 1013         """!Merge dictionary of parameters""" 
 1014         if 'flags' in params:
 
 1015             for f 
in params[
'flags']:
 
 1016                 self.task.set_flag(f[
'name'],
 
 1017                                    f.get(
'value', 
False))
 
 1018         if 'params' in params:
 
 1019             for p 
in params[
'params']:
 
 1020                 self.task.set_param(p[
'name'],
 
 1024         """!Set validity for action 
 1026         @param options dictionary with flags and params (gtask) 
 1031         for f 
in options[
'flags']:
 
 1032             if f.get(
'parameterized', 
False):
 
 1036         for p 
in options[
'params']:
 
 1037             if self.
isValid and p.get(
'required', 
False) 
and \
 
 1038                     p.get(
'value', 
'') == 
'' and \
 
 1039                     p.get(
'default', 
'') == 
'':
 
 1044         if self.parent.GetCanvas():
 
 1049         """!Check validity (all required parameters set)""" 
 1053         """!Check if action is parameterized""" 
 1057         """!Find data item by name""" 
 1059             data = rel.GetData()
 
 1060             if name == rel.GetName() 
and name 
in data.GetName():
 
 1066         """!Update action""" 
 1074         """!Draw action in canvas""" 
 1077         ogl.RectangleShape.Recentre(self, dc) 
 
 1078         ogl.RectangleShape.OnDraw(self, dc)
 
 1081     def __init__(self, parent, x, y, value = '', prompt = '', width = None, height = None):
 
 1084         @param parent window parent 
 1085         @param x, y   position of the shape 
 1086         @param fname, tname list of parameter names from / to 
 1088         @param prompt type of GIS element 
 1089         @param width,height dimension of the shape 
 1091         ModelObject.__init__(self)
 
 1099             width = UserSettings.Get(group=
'modeler', key=
'data', subkey=(
'size', 
'width'))
 
 1101             height = UserSettings.Get(group=
'modeler', key=
'data', subkey=(
'size', 
'height'))
 
 1103         if self.parent.GetCanvas():
 
 1104             ogl.EllipseShape.__init__(self, width, height)
 
 1106             self.SetCanvas(self.
parent)
 
 1109             self.SetPen(wx.BLACK_PEN)
 
 1115         """!Checks if data item is intermediate""" 
 1119         """!Set intermediate flag""" 
 1126             pen.SetStyle(wx.SHORT_DASH)
 
 1128             pen.SetStyle(wx.SOLID)
 
 1131         ogl.EllipseShape.OnDraw(self, dc)
 
 1134         """!Get logging info""" 
 1137             name.append(rel.GetName())
 
 1139             return '/'.join(name) + 
'=' + self.
value + 
' (' + self.
prompt + 
')' 
 1144         """!Get list of names""" 
 1147             name.append(rel.GetName())
 
 1173         for direction 
in (
'from', 
'to'):
 
 1175                 if direction == 
'from':
 
 1176                     action = rel.GetTo()
 
 1178                     action = rel.GetFrom()
 
 1180                 task = GUI(show = 
None).ParseCommand(cmd = action.GetLog(string = 
False))
 
 1181                 task.set_param(rel.GetName(), self.
value)
 
 1182                 action.SetParams(params = task.get_options())
 
 1185         """!Get properties dialog""" 
 1189         """!Get properties dialog""" 
 1192     def _setBrush(self):
 
 1194         if self.
prompt == 
'raster':
 
 1195             color = UserSettings.Get(group = 
'modeler', key = 
'data',
 
 1196                                      subkey = (
'color', 
'raster'))
 
 1197         elif self.
prompt == 
'raster3d':
 
 1198             color = UserSettings.Get(group = 
'modeler', key = 
'data',
 
 1199                                      subkey = (
'color', 
'raster3d'))
 
 1200         elif self.
prompt == 
'vector':
 
 1201             color = UserSettings.Get(group = 
'modeler', key = 
'data',
 
 1202                                      subkey = (
'color', 
'vector'))
 
 1204             color = UserSettings.Get(group = 
'modeler', key = 
'action',
 
 1205                                      subkey = (
'color', 
'invalid'))
 
 1206         wxColor = wx.Colour(color[0], color[1], color[2])
 
 1207         self.SetBrush(wx.Brush(wxColor))
 
 1211         isParameterized = 
False 
 1213             if rel.GetTo().IsParameterized():
 
 1214                 isParameterized = 
True 
 1216         if not isParameterized:
 
 1218                 if rel.GetFrom().IsParameterized():
 
 1219                     isParameterized = 
True 
 1223             width = int(UserSettings.Get(group = 
'modeler', key = 
'action',
 
 1224                                          subkey = (
'width', 
'parameterized')))
 
 1226             width = int(UserSettings.Get(group = 
'modeler', key = 
'action',
 
 1227                                          subkey = (
'width', 
'default')))
 
 1237             name.append(rel.GetName())
 
 1238         self.AddText(
'/'.join(name))
 
 1240             self.AddText(self.
value)
 
 1242             self.AddText(_(
'<not defined>'))
 
 1245         """!Update action""" 
 1251     """!Data - action relation""" 
 1252     def __init__(self, parent, fromShape, toShape, param = ''):
 
 1260         if self.parent.GetCanvas():        
 
 1261             ogl.LineShape.__init__(self)
 
 1264         if self 
in self.fromShape.rels:
 
 1265             self.fromShape.rels.remove(self)
 
 1266         if self 
in self.toShape.rels:
 
 1267             self.toShape.rels.remove(self)
 
 1270         """!Get id of 'from' shape""" 
 1274         """!Get id of 'to' shape""" 
 1278         """!Get related ModelData instance 
 1280         @return ModelData instance 
 1281         @return None if not found 
 1283         if isinstance(self.
fromShape, ModelData):
 
 1285         elif isinstance(self.
toShape, ModelData):
 
 1291         """!Get parameter name""" 
 1295         """!Reset related objects""" 
 1296         self.fromShape.ResetControlPoints()
 
 1297         self.toShape.ResetControlPoints()
 
 1298         self.ResetControlPoints()
 
 1301         """!Set control points""" 
 1305         """!Get list of control points""" 
 1312         pen.SetStyle(wx.SOLID)
 
 1316         """!Draw relation""" 
 1318         ogl.LineShape.OnDraw(self, dc)
 
 1324     def __init__(self, parent, x, y, id = -1, width = None, height = None, text = '', items = []):
 
 1325         """!Abstract class for loops and conditions""" 
 1326         ModelObject.__init__(self, id)
 
 1332         """!Get loop text""" 
 1336         """!Get items (id)""" 
 1344         """!Set loop text (condition)""" 
 1347         self.AddText(
'(' + str(self.
id) + 
') ' + self.
text)
 
 1352             return _(
"Condition: ") + self.
text 
 1354             return _(
"Condition: not defined")
 
 1357         """!Record relation""" 
 1358         self.rels.append(rel)
 
 1361         """!Clear object, remove rels""" 
 1365     def __init__(self, parent, x, y, id = -1, width = None, height = None, text = '', items = []):
 
 1366         """!Defines a loop""" 
 1367         ModelItem.__init__(self, parent, x, y, id, width, height, text, items)
 
 1370             width = UserSettings.Get(group=
'modeler', key=
'loop', subkey=(
'size', 
'width'))
 
 1372             height = UserSettings.Get(group=
'modeler', key=
'loop', subkey=(
'size', 
'height'))
 
 1374         if self.parent.GetCanvas():
 
 1375             ogl.RectangleShape.__init__(self, width, height)
 
 1377             self.SetCanvas(self.
parent)
 
 1380             self.SetPen(wx.BLACK_PEN)
 
 1381             self.SetCornerRadius(100)
 
 1383                 self.AddText(
'(' + str(self.
id) + 
') ' + text)
 
 1385                 self.AddText(
'(' + str(self.
id) + 
')')
 
 1389     def _setBrush(self):
 
 1392             color = UserSettings.Get(group=
'modeler', key=
'disabled',
 
 1395             color = UserSettings.Get(group=
'modeler', key=
'loop',
 
 1396                                      subkey=(
'color', 
'valid'))
 
 1398         wxColor = wx.Colour(color[0], color[1], color[2])
 
 1399         self.SetBrush(wx.Brush(wxColor))
 
 1402         """!Enable/disable action""" 
 1403         for item 
in self.
items:
 
 1404             if not isinstance(item, ModelAction):
 
 1406             item.Enable(enabled)
 
 1408         ModelObject.Enable(self, enabled)
 
 1418         """!Set items (id)""" 
 1422         """!Draw loop in canvas""" 
 1424         ogl.RectangleShape.Recentre(self, dc) 
 
 1425         ogl.RectangleShape.OnDraw(self, dc)
 
 1428     def __init__(self, parent, x, y, id = -1, width = None, height = None, text = '',
 
 1429                  items = { 
'if' : [], 
'else' : [] }):
 
 1430         """!Defines a if-else condition""" 
 1431         ModelItem.__init__(self, parent, x, y, id, width, height, text, items)
 
 1434             self.
width = UserSettings.Get(group=
'modeler', key=
'if-else', subkey=(
'size', 
'width'))
 
 1438             self.
height = UserSettings.Get(group=
'modeler', key=
'if-else', subkey=(
'size', 
'height'))
 
 1442         if self.parent.GetCanvas():
 
 1443             ogl.PolygonShape.__init__(self)
 
 1445             points = [(0, - self.
height / 2),
 
 1446                       (self.
width / 2, 0),
 
 1448                       (- self.
width / 2, 0)]
 
 1451             self.SetCanvas(self.
parent)
 
 1454             self.SetPen(wx.BLACK_PEN)
 
 1456                 self.AddText(
'(' + str(self.
id) + 
') ' + text)
 
 1458                 self.AddText(
'(' + str(self.
id) + 
')')
 
 1465         """!Get object width""" 
 1469         """!Get object height""" 
 1475         @param items list of items 
 1476         @param branch 'if' / 'else' 
 1478         if branch 
in [
'if', 
'else']:
 
 1479             self.
items[branch] = items
 
 1482     """!Process GRASS model file (gxm)""" 
 1484         """!A ElementTree handler for the GXM XML file, as defined in 
 1504     def _filterValue(self, value):
 
 1509         value = value.replace(
'<', 
'<')
 
 1510         value = value.replace(
'>', 
'>')
 
 1514     def _getNodeText(self, node, tag, default = ''):
 
 1515         """!Get node text""" 
 1525     def _processWindow(self):
 
 1526         """!Process window properties""" 
 1527         node = self.root.find(
'window')
 
 1534     def _processProperties(self):
 
 1535         """!Process model properties""" 
 1536         node = self.root.find(
'properties')
 
 1539         for key 
in (
'name', 
'description', 
'author'):
 
 1542         for f 
in node.findall(
'flag'):
 
 1543             name = f.get(
'name', 
'')
 
 1544             if name == 
'overwrite':
 
 1547     def _processProperty(self, pnode, name):
 
 1548         """!Process given property""" 
 1549         node = pnode.find(name)
 
 1550         if node 
is not None:
 
 1555     def _processVariables(self):
 
 1556         """!Process model variables""" 
 1557         vnode = self.root.find(
'variables')
 
 1560         for node 
in vnode.findall(
'variable'):
 
 1561             name = node.get(
'name', 
'')
 
 1564             self.
variables[name] = { 
'type' : node.get(
'type', 
'string') }
 
 1565             for key 
in (
'description', 
'value'):
 
 1568     def _processVariable(self, pnode, name, key):
 
 1569         """!Process given variable""" 
 1570         node = pnode.find(key)
 
 1571         if node 
is not None:
 
 1575     def _processItems(self):
 
 1576         """!Process model items (actions, loops, conditions)""" 
 1581     def _processActions(self):
 
 1582         """!Process model file""" 
 1583         for action 
in self.root.findall(
'action'):
 
 1584             pos, size = self.
_getDim(action)
 
 1587             task = action.find(
'task')
 
 1588             if task 
is not None:
 
 1589                 if task.find(
'disabled') 
is not None:
 
 1595             aId = int(action.get(
'id', -1))
 
 1597             self.actions.append({ 
'pos'      : pos,
 
 1601                                   'disabled' : disabled })
 
 1603     def _getDim(self, node):
 
 1604         """!Get position and size of shape""" 
 1606         posAttr = node.get(
'pos', 
None)
 
 1608             posVal = map(int, posAttr.split(
','))
 
 1610                 pos = (posVal[0], posVal[1])
 
 1614         sizeAttr = node.get(
'size', 
None)
 
 1616             sizeVal = map(int, sizeAttr.split(
','))
 
 1618                 size = (sizeVal[0], sizeVal[1])
 
 1624     def _processData(self):
 
 1625         """!Process model file""" 
 1626         for data 
in self.root.findall(
'data'):
 
 1627             pos, size = self.
_getDim(data)
 
 1628             param = data.find(
'data-parameter')
 
 1629             prompt = value = 
None 
 1630             if param 
is not None:
 
 1631                 prompt = param.get(
'prompt', 
None)
 
 1634             if data.find(
'intermediate') 
is None:
 
 1635                 intermediate = 
False 
 1640             for rel 
in data.findall(
'relation'):
 
 1641                 defrel = { 
'id'  : int(rel.get(
'id', -1)),
 
 1642                            'dir' : rel.get(
'dir', 
'to'),
 
 1643                            'name' : rel.get(
'name', 
'') }
 
 1645                 for point 
in rel.findall(
'point'):
 
 1648                     points.append((float(x), float(y)))
 
 1649                 defrel[
'points'] = points
 
 1652             self.data.append({ 
'pos' : pos,
 
 1656                                'intermediate' : intermediate,
 
 1659     def _processTask(self, node):
 
 1662         @return grassTask instance 
 1663         @return None on error 
 1666         parameterized = list()
 
 1668         name = node.get(
'name', 
None)
 
 1675         for f 
in node.findall(
'flag'):
 
 1676             flag = f.get(
'name', 
'')
 
 1677             if f.get(
'parameterized', 
'0') == 
'1':
 
 1678                 parameterized.append((
'flag', flag))
 
 1679                 if f.get(
'value', 
'1') == 
'0':
 
 1682                 cmd.append(
'--' + flag)
 
 1684                 cmd.append(
'-' + flag)
 
 1686         for p 
in node.findall(
'parameter'):
 
 1687             name = p.get(
'name', 
'')
 
 1688             if p.find(
'parameterized') 
is not None:
 
 1689                 parameterized.append((
'param', name))
 
 1690             cmd.append(
'%s=%s' % (name,
 
 1693         task, err = GUI(show = 
None, checkError = 
True).ParseCommand(cmd = cmd)
 
 1695             GWarning(os.linesep.join(err))
 
 1697         for opt, name 
in parameterized:
 
 1699                 task.set_flag(name, 
True, element = 
'parameterized')
 
 1701                 task.set_param(name, 
True, element = 
'parameterized')
 
 1705     def _processLoops(self):
 
 1706         """!Process model loops""" 
 1707         for node 
in self.root.findall(
'loop'):
 
 1708             pos, size = self.
_getDim(node)
 
 1711             for anode 
in node.findall(
'item'):
 
 1713                     aid.append(int(anode.text))
 
 1717             self.loops.append({ 
'pos'     : pos,
 
 1720                                 'id'      : int(node.get(
'id', -1)),
 
 1723     def _processConditions(self):
 
 1724         """!Process model conditions""" 
 1725         for node 
in self.root.findall(
'if-else'):
 
 1726             pos, size = self.
_getDim(node)
 
 1728             aid = { 
'if'   : list(),
 
 1730             for b 
in aid.keys():
 
 1731                 bnode = node.find(b)
 
 1734                 for anode 
in bnode.findall(
'item'):
 
 1736                         aid[b].append(int(anode.text))
 
 1740             self.conditions.append({ 
'pos'     : pos,
 
 1743                                      'id'      : int(node.get(
'id', -1)),
 
 1747     """!Generic class for writing model file""" 
 1765         for action 
in model.GetItems(objType = ModelAction):
 
 1766             for rel 
in action.GetRelations():
 
 1767                 dataItem = rel.GetData()
 
 1768                 if dataItem 
not in dataList:
 
 1769                     dataList.append(dataItem)
 
 1770         self.
_data(dataList)
 
 1774     def _filterValue(self, value):
 
 1775         """!Make value XML-valid""" 
 1776         value = value.replace(
'<', 
'<')
 
 1777         value = value.replace(
'>', 
'>')
 
 1783         self.fd.write(
'<?xml version="1.0" encoding="%s"?>\n' % 
GetDefaultEncoding(forceUTF8 = 
True))
 
 1784         self.fd.write(
'<!DOCTYPE gxm SYSTEM "grass-gxm.dtd">\n')
 
 1785         self.fd.write(
'%s<gxm>\n' % (
' ' * self.
indent))
 
 1791         self.fd.write(
'%s</gxm>\n' % (
' ' * self.
indent))
 
 1794         """!Write window properties""" 
 1795         canvas = self.model.GetCanvas()
 
 1799         pos  = win.GetPosition()
 
 1800         size = win.GetSize()
 
 1801         self.fd.write(
'%s<window pos="%d,%d" size="%d,%d" />\n' % \
 
 1802                           (
' ' * self.
indent, pos[0], pos[1], size[0], size[1]))
 
 1804     def _properties(self):
 
 1805         """!Write model properties""" 
 1806         self.fd.write(
'%s<properties>\n' % (
' ' * self.
indent))
 
 1811             self.fd.write(
'%s<description>%s</description>\n' % (
' ' * self.
indent,
 
 1814             self.fd.write(
'%s<author>%s</author>\n' % (
' ' * self.
indent,
 
 1819             self.fd.write(
'%s<flag name="overwrite" />\n' % (
' ' * self.
indent))
 
 1821         self.fd.write(
'%s</properties>\n' % (
' ' * self.
indent))
 
 1823     def _variables(self):
 
 1824         """!Write model variables""" 
 1827         self.fd.write(
'%s<variables>\n' % (
' ' * self.
indent))
 
 1829         for name, values 
in self.variables.iteritems():
 
 1830             self.fd.write(
'%s<variable name="%s" type="%s">\n' % \
 
 1833             if 'value' in values:
 
 1834                 self.fd.write(
'%s<value>%s</value>\n' % \
 
 1836             if 'description' in values:
 
 1837                 self.fd.write(
'%s<description>%s</description>\n' % \
 
 1840             self.fd.write(
'%s</variable>\n' % (
' ' * self.
indent))
 
 1842         self.fd.write(
'%s</variables>\n' % (
' ' * self.
indent))
 
 1845         """!Write actions/loops/conditions""" 
 1846         for item 
in self.
items:
 
 1847             if isinstance(item, ModelAction):
 
 1849             elif isinstance(item, ModelLoop):
 
 1851             elif isinstance(item, ModelCondition):
 
 1854     def _action(self, action):
 
 1855         """!Write actions""" 
 1856         self.fd.write(
'%s<action id="%d" name="%s" pos="%d,%d" size="%d,%d">\n' % \
 
 1857                           (
' ' * self.
indent, action.GetId(), action.GetName(), action.GetX(), action.GetY(),
 
 1858                            action.GetWidth(), action.GetHeight()))
 
 1860         self.fd.write(
'%s<task name="%s">\n' % (
' ' * self.
indent, action.GetLog(string = 
False)[0]))
 
 1862         if not action.IsEnabled():
 
 1863             self.fd.write(
'%s<disabled />\n' % (
' ' * self.
indent))
 
 1864         for key, val 
in action.GetParams().iteritems():
 
 1867                     if f.get(
'value', 
False) 
or f.get(
'parameterized', 
False):
 
 1868                         if f.get(
'parameterized', 
False):
 
 1869                             if f.get(
'value', 
False) == 
False:
 
 1870                                 self.fd.write(
'%s<flag name="%s" value="0" parameterized="1" />\n' %
 
 1871                                               (
' ' * self.
indent, f.get(
'name', 
'')))
 
 1873                                 self.fd.write(
'%s<flag name="%s" parameterized="1" />\n' %
 
 1874                                               (
' ' * self.
indent, f.get(
'name', 
'')))
 
 1876                             self.fd.write(
'%s<flag name="%s" />\n' %
 
 1877                                           (
' ' * self.
indent, f.get(
'name', 
'')))
 
 1880                     if not p.get(
'value', 
'') 
and not p.get(
'parameterized', 
False):
 
 1882                     self.fd.write(
'%s<parameter name="%s">\n' %
 
 1883                                   (
' ' * self.
indent, p.get(
'name', 
'')))
 
 1885                     if p.get(
'parameterized', 
False):
 
 1886                         self.fd.write(
'%s<parameterized />\n' % (
' ' * self.
indent))
 
 1887                     self.fd.write(
'%s<value>%s</value>\n' %
 
 1890                     self.fd.write(
'%s</parameter>\n' % (
' ' * self.
indent))
 
 1892         self.fd.write(
'%s</task>\n' % (
' ' * self.
indent))
 
 1894         self.fd.write(
'%s</action>\n' % (
' ' * self.
indent))
 
 1896     def _data(self, dataList):
 
 1898         for data 
in dataList:
 
 1899             self.fd.write(
'%s<data pos="%d,%d" size="%d,%d">\n' % \
 
 1900                               (
' ' * self.
indent, data.GetX(), data.GetY(),
 
 1901                                data.GetWidth(), data.GetHeight()))
 
 1903             self.fd.write(
'%s<data-parameter prompt="%s">\n' % \
 
 1904                               (
' ' * self.
indent, data.GetPrompt()))
 
 1906             self.fd.write(
'%s<value>%s</value>\n' %
 
 1909             self.fd.write(
'%s</data-parameter>\n' % (
' ' * self.
indent))
 
 1911             if data.IsIntermediate():
 
 1912                 self.fd.write(
'%s<intermediate />\n' % (
' ' * self.
indent))
 
 1915             for ft 
in (
'from', 
'to'):
 
 1916                 for rel 
in data.GetRelations(ft):
 
 1918                         aid = rel.GetTo().GetId()
 
 1920                         aid  = rel.GetFrom().GetId()
 
 1921                     self.fd.write(
'%s<relation dir="%s" id="%d" name="%s">\n' % \
 
 1922                                       (
' ' * self.
indent, ft, aid, rel.GetName()))
 
 1924                     for point 
in rel.GetLineControlPoints()[1:-1]:
 
 1925                         self.fd.write(
'%s<point>\n' % (
' ' * self.
indent))
 
 1928                         self.fd.write(
'%s<x>%d</x>\n' % (
' ' * self.
indent, int(x)))
 
 1929                         self.fd.write(
'%s<y>%d</y>\n' % (
' ' * self.
indent, int(y)))
 
 1931                         self.fd.write(
'%s</point>\n' % (
' ' * self.
indent))
 
 1933                     self.fd.write(
'%s</relation>\n' % (
' ' * self.
indent))
 
 1936             self.fd.write(
'%s</data>\n' % (
' ' * self.
indent))
 
 1938     def _loop(self, loop):
 
 1940         self.fd.write(
'%s<loop id="%d" pos="%d,%d" size="%d,%d">\n' % \
 
 1941                           (
' ' * self.
indent, loop.GetId(), loop.GetX(), loop.GetY(),
 
 1942                            loop.GetWidth(), loop.GetHeight()))
 
 1943         text = loop.GetText()
 
 1946             self.fd.write(
'%s<condition>%s</condition>\n' %
 
 1948         for item 
in loop.GetItems():
 
 1949             self.fd.write(
'%s<item>%d</item>\n' %
 
 1950                           (
' ' * self.
indent, item.GetId()))
 
 1952         self.fd.write(
'%s</loop>\n' % (
' ' * self.
indent))
 
 1954     def _condition(self, condition):
 
 1955         """!Write conditions""" 
 1956         bbox = condition.GetBoundingBoxMin()
 
 1957         self.fd.write(
'%s<if-else id="%d" pos="%d,%d" size="%d,%d">\n' % \
 
 1958                           (
' ' * self.
indent, condition.GetId(), condition.GetX(), condition.GetY(),
 
 1960         text = condition.GetText()
 
 1963             self.fd.write(
'%s<condition>%s</condition>\n' %
 
 1965         items = condition.GetItems()
 
 1966         for b 
in items.keys():
 
 1967             if len(items[b]) < 1:
 
 1969             self.fd.write(
'%s<%s>\n' % (
' ' * self.
indent, b))
 
 1971             for item 
in items[b]:
 
 1972                 self.fd.write(
'%s<item>%d</item>\n' %
 
 1973                               (
' ' * self.
indent, item.GetId()))
 
 1975             self.fd.write(
'%s</%s>\n' % (
' ' * self.
indent, b))
 
 1978         self.fd.write(
'%s</if-else>\n' % (
' ' * self.
indent))
 
 1982         """!Class for exporting model to Python script 
 1984         @param fd file desciptor 
 1992     def _writePython(self):
 
 1993         """!Write model to file""" 
 1994         properties = self.model.GetProperties()
 
 1997 r"""#!/usr/bin/env python 
 2013        EncodeString(
'\n# '.join(properties[
'description'].splitlines())),
 
 2023 import grass.script as grass 
 2027         rast, vect, rast3d, msg = self.model.GetIntermediateData()
 
 2034 r"""    grass.run_command('g.remove', 
 2036 """ % 
','.join(map(
lambda x: 
"'" + x + 
"'", rast)))
 
 2039 r"""    grass.run_command('g.remove', 
 2041 """ % 
','.join(map(
lambda x: 
"'" + x + 
"'", vect)))
 
 2044 r"""    grass.run_command('g.remove', 
 2046 """ % 
','.join(map(
lambda x: 
"'" + x + 
"'", rast3d)))
 
 2047         if not rast 
and not vect 
and not rast3d:
 
 2048             self.fd.write(
'    pass\n')
 
 2050         self.fd.write(
"\ndef main():\n")
 
 2051         for item 
in self.model.GetItems():
 
 2054         self.fd.write(
"\n    return 0\n")
 
 2058 if __name__ == "__main__": 
 2059     options, flags = grass.parser() 
 2060     atexit.register(cleanup) 
 2064     def _writePythonItem(self, item, ignoreBlock = True, variables = []):
 
 2065         """!Write model object to Python file""" 
 2066         if isinstance(item, ModelAction):
 
 2067             if ignoreBlock 
and item.GetBlockId(): 
 
 2070         elif isinstance(item, ModelLoop) 
or isinstance(item, ModelCondition):
 
 2072             variables = self.model.GetVariables()
 
 2073             cond = item.GetText()
 
 2074             for variable 
in variables:
 
 2075                 pattern = re.compile(
'%' + variable)
 
 2076                 if pattern.search(cond):
 
 2077                     value = variables[variable].get(
'value', 
'')
 
 2078                     if variables[variable].get(
'type', 
'string') == 
'string':
 
 2079                         value = 
'"' + value + 
'"' 
 2080                     cond = pattern.sub(value, cond)
 
 2081             if isinstance(item, ModelLoop):
 
 2082                 condVar, condText = map(
lambda x: x.strip(), re.split(
'\s*in\s*', cond))
 
 2083                 cond = 
"%sfor %s in " % (
' ' * self.
indent, condVar)
 
 2084                 if condText[0] == 
'`' and condText[-1] == 
'`':
 
 2085                     task = GUI(show = 
None).ParseCommand(cmd = 
utils.split(condText[1:-1]))
 
 2086                     cond += 
"grass.read_command(" 
 2087                     cond += self.
_getPythonActionCmd(task, len(cond), variables = [condVar]) + 
".splitlines()" 
 2090                 self.fd.write(
'%s:\n' % cond)
 
 2092                 for action 
in item.GetItems():
 
 2096                 self.fd.write(
'%sif %s:\n' % (
' ' * self.
indent, cond))
 
 2098                 condItems = item.GetItems()
 
 2099                 for action 
in condItems[
'if']:
 
 2101                 if condItems[
'else']:
 
 2103                     self.fd.write(
'%selse:\n' % (
' ' * self.
indent))
 
 2105                     for action 
in condItems[
'else']:
 
 2109     def _writePythonAction(self, item, variables = []):
 
 2110         """!Write model action to Python file""" 
 2111         task = GUI(show = 
None).ParseCommand(cmd = item.GetLog(string = 
False, substitute = self.model.GetVariables()))
 
 2112         strcmd = 
"%sgrass.run_command(" % (
' ' * self.
indent)
 
 2115     def _getPythonActionCmd(self, task, cmdIndent, variables = []):
 
 2116         opts = task.get_options()
 
 2122         for f 
in opts[
'flags']:
 
 2123             if f.get(
'value', 
False):
 
 2124                 name = f.get(
'name', 
'')
 
 2126                     params.append(
'%s = True' % name)
 
 2130         for p 
in opts[
'params']:
 
 2131             name = p.get(
'name', 
None)
 
 2132             value = p.get(
'value', 
None)
 
 2134                 ptype = p.get(
'type', 
'string')
 
 2136                     params.append(
"%s = %s" % (name, value[1:]))
 
 2137                 elif ptype == 
'string':
 
 2138                     params.append(
'%s = "%s"' % (name, value))
 
 2140                     params.append(
"%s = %s" % (name, value))
 
 2142         ret += 
'"%s"' % task.get_name()
 
 2144             ret += 
",\n%sflags = '%s'" % (
' ' * cmdIndent, flags)
 
 2147             for opt 
in params[:-1]:
 
 2148                 ret += 
"%s%s,\n" % (
' ' * cmdIndent, opt)
 
 2149             ret += 
"%s%s)" % (
' ' * cmdIndent, params[-1])
 
 2156     def __init__(self, parent, params, id = wx.ID_ANY, title = _(
"Model parameters"),
 
 2157                  style = wx.DEFAULT_DIALOG_STYLE | wx.RESIZE_BORDER, **kwargs):
 
 2158         """!Model parameters dialog 
 2164         wx.Dialog.__init__(self, parent = parent, id = id, title = title, style = style, **kwargs)
 
 2167                                   style = globalvar.FNPageDStyle)
 
 2170         wx.CallAfter(self.notebook.SetSelection, 0)
 
 2173         self.
interData = wx.CheckBox(parent = self, label = _(
"Delete intermediate data when finish"))
 
 2174         self.interData.SetValue(
True)
 
 2175         rast, vect, rast3d, msg = self.parent.GetModel().GetIntermediateData()
 
 2176         if not rast 
and not vect 
and not rast3d:
 
 2177             self.interData.Hide()
 
 2179         self.
btnCancel = wx.Button(parent = self, id = wx.ID_CANCEL)
 
 2180         self.
btnRun    = wx.Button(parent = self, id = wx.ID_OK,
 
 2182         self.btnRun.SetDefault()
 
 2186         size = self.GetBestSize()
 
 2187         self.SetMinSize(size)
 
 2188         self.SetSize((size.width, size.height +
 
 2189                       panel.constrained_size[1] -
 
 2190                       panel.panelMinHeight))
 
 2193         btnSizer = wx.StdDialogButtonSizer()
 
 2195         btnSizer.AddButton(self.
btnRun)
 
 2198         mainSizer = wx.BoxSizer(wx.VERTICAL)
 
 2199         mainSizer.Add(item = self.
notebook, proportion = 1,
 
 2201         if self.interData.IsShown():
 
 2202             mainSizer.Add(item = self.
interData, proportion = 0,
 
 2203                           flag = wx.EXPAND | wx.ALL | wx.ALIGN_CENTER, border = 5)
 
 2205             mainSizer.Add(item = wx.StaticLine(parent = self, id = wx.ID_ANY,
 
 2206                                                style = wx.LI_HORIZONTAL),
 
 2208                           flag = wx.EXPAND | wx.LEFT | wx.RIGHT, border = 5) 
 
 2210         mainSizer.Add(item = btnSizer, proportion = 0,
 
 2211                       flag = wx.EXPAND | wx.ALL | wx.ALIGN_CENTER, border = 5)
 
 2213         self.SetSizer(mainSizer)
 
 2216     def _createPages(self):
 
 2217         """!Create for each parameterized module its own page""" 
 2218         nameOrdered = [
''] * len(self.params.keys())
 
 2219         for name, params 
in self.params.iteritems():
 
 2220             nameOrdered[params[
'idx']] = name
 
 2221         for name 
in nameOrdered:
 
 2222             params = self.
params[name]
 
 2224             if name == 
'variables':
 
 2225                 name = _(
'Variables')
 
 2226             self.notebook.AddPage(page = panel, text = name)
 
 2230     def _createPage(self, name, params):
 
 2231         """!Define notebook page""" 
 2232         if name 
in globalvar.grassCmd:
 
 2233             task = gtask.grassTask(name)
 
 2235             task = gtask.grassTask()
 
 2236         task.flags  = params[
'flags']
 
 2237         task.params = params[
'params']
 
 2239         panel = CmdPanel(parent = self, id = wx.ID_ANY, task = task)
 
 2240         self.tasks.append(task)
 
 2245         """!Check for errors, get list of messages""" 
 2247         for task 
in self.
tasks:
 
 2248             errList += task.get_cmd_error()
 
 2253         """!Check if to detele intermediate data""" 
 2254         if self.interData.IsShown() 
and self.interData.IsChecked():
 
def CmdToTuple
Convert command list to tuple for gcmd.RunCommand() 
 
def GetItems
Get list of model items. 
 
def _processActions
Process model file. 
 
def normalize_whitespace
Remove redundant whitespace from a string. 
 
def EncodeString
Return encoded string using system locales. 
 
def _writePython
Write model to file. 
 
def GetPropDialog
Get properties dialog. 
 
def _processVariable
Process given variable. 
 
def Clear
Clear object, remove rels. 
 
def IsEnabled
Get True if action is enabled, otherwise False. 
 
def _filterValue
Make value XML-valid. 
 
def _properties
Write model properties. 
 
def DeleteIntermediateData
Check if to detele intermediate data. 
 
def __init__
Model parameters dialog. 
 
def SetText
Set loop text (condition) 
 
Generic class for writing model file. 
 
def _getDim
Get position and size of shape. 
 
def SetParams
Set dictionary of parameters. 
 
def FindData
Find data item by name. 
 
def _processConditions
Process model conditions. 
 
Action class (GRASS module) 
 
def GetPropDialog
Get properties dialog. 
 
def SetVariables
Set model variables. 
 
def GetParams
Get dictionary of parameters. 
 
def GetNumItems
Get number of items. 
 
def _processProperties
Process model properties. 
 
def _processWindow
Process window properties. 
 
def _processLoops
Process model loops. 
 
def GetRelations
Get list of relations. 
 
Class representing the model. 
 
def ResetShapes
Reset related objects. 
 
def GetItems
Get items (id) 
 
def _createPage
Define notebook page. 
 
def __init__
Abstract class for loops and conditions. 
 
def _items
Write actions/loops/conditions. 
 
def GetBlock
Get list of related ModelObject(s) which defines block (loop/condition) 
 
def __init__
Defines a loop. 
 
def Parameterize
Return parameterized options. 
 
def GetText
Get loop text. 
 
def RunAction
Run given action. 
 
def GetLog
Get logging info. 
 
def __init__
Class for exporting model to Python script. 
 
def FindData
Find data item in the model. 
 
def SetProperties
Record properties dialog. 
 
def Enable
Enable/disable action. 
 
def Validate
Validate model, return None if model is valid otherwise error string. 
 
def GetTo
Get id of 'to' shape. 
 
def IsIntermediate
Checks if data item is intermediate. 
 
def GetBlockId
Get list of related ids which defines block. 
 
def SetControlPoints
Set control points. 
 
def split
Platform spefic shlex.split. 
 
def AddRelation
Record relation. 
 
def _processData
Process model file. 
 
def _substituteFile
Subsitute variables in command file inputs. 
 
def _condition
Write conditions. 
 
def IsParameterized
Return True if model is parameterized. 
 
def GetHeight
Get object height. 
 
def GetIntermediateData
Get info about intermediate data. 
 
def RemoveItem
Remove item from model. 
 
def SetIntermediate
Set intermediate flag. 
 
def Enable
Enable/disable action. 
 
def SetBlock
Add object to the block (loop/condition) 
 
def OnDraw
Draw loop in canvas. 
 
def GetLog
Get logging info. 
 
def LoadModel
Load model definition stored in GRASS Model XML file (gxm) 
 
def EncodeString
Return encoded string using system locales. 
 
def _processItems
Process model items (actions, loops, conditions) 
 
def AddItem
Add item to the list. 
 
def _processProperty
Process given property. 
 
def SetItems
Set items (id) 
 
def SetPropDialog
Get properties dialog. 
 
def GetErrors
Check for errors, get list of messages. 
 
def GetDefaultEncoding
Get default system encoding. 
 
def GetData
Get related ModelData instance. 
 
def GetNextId
Get next id (data ignored) 
 
def _processTask
Process task. 
 
def AddRelation
Record new relation. 
 
def MergeParams
Merge dictionary of parameters. 
 
def GetControlPoints
Get list of control points. 
 
def _filterValue
Filter value. 
 
def SetValid
Set validity for action. 
 
def __init__
A ElementTree handler for the GXM XML file, as defined in grass-gxm.dtd. 
 
def GetName
Get list of names. 
 
def _processVariables
Process model variables. 
 
def GetName
Get parameter name. 
 
def OnDraw
Draw action in canvas. 
 
def _action
Write actions. 
 
def _writePythonItem
Write model object to Python file. 
 
def IsValid
Check validity (all required parameters set) 
 
Process GRASS model file (gxm) 
 
def GetCanvas
Get canvas or None. 
 
def _createPages
Create for each parameterized module its own page. 
 
def GetData
Get list of data items. 
 
def _variables
Write model variables. 
 
def _window
Write window properties. 
 
def GetTask
Get grassTask instance. 
 
def GetItem
Get item of given id. 
 
def DeleteIntermediateData
Detele intermediate data. 
 
def GetVariables
Get model variables. 
 
def GetProperties
Get model properties. 
 
def FindAction
Find action by id. 
 
def SetItems
Set items (id) 
 
def RunCommand
Run GRASS command. 
 
def _writePythonAction
Write model action to Python file. 
 
def UnSetBlock
Remove object from the block (loop/consition) 
 
def GetWidth
Get object width. 
 
def _getNodeText
Get node text. 
 
def GetFrom
Get id of 'from' shape.